Rust

What is Rust?

Why should we Care?

Over-Overview

  • Sponsored by Mozilla
    • Quantum/Servo (Firefox)
  • "Systems programming language"
  • Focus on "Safety"

Ecosystem

  • Build tools: "rustc"
  • Dependency management system: "cargo"
    • ~20k packages available
  •  

Language Features

  • "Zero Cost Abstractions"
  • Type Safety
  • Memory Safety
  • Error Safety
  • "Modern" features
    • Iteration
    • Operator overloading
    • ...
  • Extensible Type system using "Traits"

Why should we care?

  • Safety
  • Performance
  • Integrations
    • Python extensions
    • Compilation to WebAssembly

Hello World

fn main() {
    println!("Hello World!");
}
$ rustc hello.rs
$ ./hello
Hello World!

Flow Control

fn main() {
    let n = 5;

    if n < 0 {
        print!("{} is negative", n);
    } else if n > 0 {
        print!("{} is positive", n);
    } else {
        print!("{} is zero", n);
    }

    let big_n =
        if n < 10 && n > -10 {
            println!(", and is a small number, increase ten-fold");
            10 * n
        } else {
            println!(", and is a big number, half the number");
            n / 2
        };

    println!("{} -> {}", n, big_n);
}

Variables

fn main() {
    let n = 5;
    n = 10; // <- Error
}

Variables are immutable by default

fn main() {
    let n;
    println!("My number: {}", n); // <- Error
    n = 10;
}

It is not possible to use a variable before initialization

fn main() {
    let mut n = 5;
    n = 10;
}

Mutable variables must be declared

Functions

fn my_function() {
    println!("Hi!");
}

Function declatation

fn typedFunction(num: i64) -> f64 {
    println!("Got: {}", num);
    return 6.4;
}

Arguments + return type

fn multipleValues() => (i64, f64) {
    (1, 2.0)
}

Multiple return values

Ownership

fn main() {
    let n = 5;
    n = 10; // <- Error
}

Variables are immutable by default

fn main() {
    let n;
    println!("My number: {}", n); // <- Error
    n = 10;
}

It is not possible to use a variable before initialization

fn main() {
    let mut n = 5;
    n = 10;
}

Mutable variables must be declared

Structures

struct Nil; // "unit" struct

struct Pair(i32, f32); // tuple struct

struct Point { // struct with two fields
    x: f32,
    y: f32,
}

struct Rectangle { // nested struct
    p1: Point,
    p2: Point,
}

Structured type declarations

fn main() {
    let point = Point { x: 0.3, y: 0.5 };

    let rect = Rectangle {
        p1: p1,
        p2: Point { x: 2.3, y: 5.5 },
    };

    println!("My rectangle: [{}, {}] -> [{}, {}]",
        rect.p1.x, rect.p1.y, rect.p2.x, rect.p2.y
    );
}

Usage

Enum & Pattern Matching

enum WebEvent {
    PageLoad,
    PageUnload,
    KeyPress(char),
    Paste(string),
    Click { x: i64, y: i64 },
}

Declaring an enum

fn inspect(event: WebEvent) {
    match event {
        WebEvent::PageLoad => println!("page loaded"),
        WebEvent::PageUnload => println!("page unloaded"),
        // Destructure `c` from inside the `enum`.
        WebEvent::KeyPress(c) => println!("pressed '{}'.", c),
        WebEvent::Paste(s) => println!("pasted \"{}\".", s),
        // Destructure `Click` into `x` and `y`.
        WebEvent::Click { x, y } => {
            println!("clicked at x={}, y={}.", x, y);
        },
    }
}

simple matching

Pattern Matching Cont.

fn is_prime(number: u64) {
    match number {
        1 => println!("One!"),
        2 | 3 | 5 | 7 | 11 => println!("This is a prime!"),
        13...19 => println!("Probably a prime!"),
        _ => println!("Likely not a prime!"),
    }
}

Matching integer values

Variables

fn main() {
    let n = 5;
    n = 10; // <- Error
}

Variables are immutable by default

fn main() {
    let n;
    println!("My number: {}", n); // <- Error
    n = 10;
}

It is not possible to use a variable before initialization

fn main() {
    let mut n = 5;
    n = 10;
}

Mutable variables must be declared

deck

By Fabian Schindler

deck

  • 213