Skip to main content

Getting Started with Rust Programming

Created: March 9, 2026 CalmOps 4 min read

Introduction

Rust is a systems programming language that guarantees memory safety without garbage collection. It has gained massive popularity for building fast, reliable software. This guide introduces Rust fundamentals.

Why Rust

Key Features

  • Memory safety without GC
  • Zero-cost abstractions
  • Fearless concurrency
  • Modern tooling
  • Great error messages

Use Cases

  • WebAssembly
  • CLI tools
  • Systems programming
  • Web backends
  • Blockchain

Setting Up

Installation

curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh

Project Setup

cargo new hello_rust
cd hello_rust
cargo run

Project Structure

hello_rust/
├── src/
│   └── main.rs
├── Cargo.toml
└── Cargo.lock

Basics

Hello World

fn main() {
    println!("Hello, world!");
}

Variables

let x = 5;           // immutable by default
let mut y = 10;      // mutable

let age: u32 = 25;   // explicit type

Data Types

// Integer
let i: i32 = 42;
let u: u64 = 100;

// Float
let f: f64 = 3.14;

// Boolean
let b: bool = true;

// Character
let c: char = 'A';

// Tuple
let tup: (i32, f64, u8) = (500, 6.4, 1);

// Array
let arr: [i32; 5] = [1, 2, 3, 4, 5];

Ownership and Borrowing

Ownership Rules

  1. Each value has one owner
  2. When owner goes out of scope, value drops
  3. Only one owner at a time
fn main() {
    let s1 = String::from("hello");
    let s2 = s1;  // s1 moves to s2
    
    // println!("{}", s1);  // ERROR: s1 no longer valid
    println!("{}", s2);    // Works fine
}

Borrowing

fn calculate_length(s: &String) -> usize {
    s.len()
}

fn main() {
    let s1 = String::from("hello");
    let len = calculate_length(&s1);  // Borrow s1
    
    println!("Length of '{}' is {}", s1, len);  // s1 still valid
}

Mutable Borrowing

fn main() {
    let mut s = String::from("hello");
    
    change(&mut s);
    
    println!("{}", s);  // "hello, world"
}

fn change(some_string: &mut String) {
    some_string.push_str(", world");
}

Functions

fn add(a: i32, b: i32) -> i32 {
    a + b
}

fn main() {
    let result = add(5, 3);
    println!("{}", result);
}

Control Flow

If/Else

let number = 6;

if number % 2 == 0 {
    println!("Even");
} else {
    println!("Odd");
}

Match

let coin = "penny";

let value = match coin {
    "penny" => 1,
    "nickel" => 5,
    "dime" => 10,
    "quarter" => 25,
    _ => 0,
};

Loops

// Loop with return value
let mut counter = 0;
let result = loop {
    counter += 1;
    if counter == 10 {
        break counter * 2;
    }
};

// While
while counter > 0 {
    counter -= 1;
}

// For
let a = [10, 20, 30, 40, 50];
for element in a.iter() {
    println!("{}", element);
}

Structs and Enums

Structs

struct User {
    username: String,
    email: String,
    active: bool,
}

fn main() {
    let user = User {
        username: String::from("john"),
        email: String::from("[email protected]"),
        active: true,
    };
    
    println!("{}", user.username);
}

Enums

enum Message {
    Quit,
    Move { x: i32, y: i32 },
    Write(String),
    ChangeColor(i32, i32, i32),
}

Error Handling

Option and Result

fn divide(a: f64, b: f64) -> Option<f64> {
    if b == 0.0 {
        None
    } else {
        Some(a / b)
    }
}

fn main() {
    match divide(10.0, 2.0) {
        Some(result) => println!("{}", result),
        None => println!("Cannot divide by zero"),
    }
}

Panic

// Unrecoverable errors
panic!("crash and burn");

Collections

Vectors

let mut v = vec![1, 2, 3];
v.push(4);
v.push(5);

for i in &v {
    println!("{}", i);
}

Strings

let s1 = String::from("hello");
let s2 = " world";
let s3 = s1 + s2;

println!("{}", s3);

Hash Maps

use std::collections::HashMap;

let mut scores = HashMap::new();
scores.insert("Blue", 10);
scores.insert("Yellow", 50);

for (key, value) in &scores {
    println!("{}: {}", key, value);
}

Packages and Crates

Cargo.toml

[package]
name = "hello_rust"
version = "0.1.0"
edition = "2021"

[dependencies]
serde = "1.0"
reqwest = "0.11"

Using Crates

use serde::{Deserialize, Serialize};

#[derive(Serialize, Deserialize)]
struct Person {
    name: String,
    age: u32,
}

What’s Next

Learning Path

  1. Ownership and borrowing
  2. Structs, enums, pattern matching
  3. Error handling
  4. Collections
  5. Lifetimes
  6. Concurrency

Resources

Conclusion

Rust offers a unique combination of safety and performance. Start with the basics, focus on understanding ownership, and build projects to learn. The compiler is your friend—it will teach you safe Rust patterns.


Resources

Comments

Share this article

Scan to read on mobile