Generics

📖 Sometimes, when writing a function or data type, we may want it to work for multiple types of arguments. In Rust, we can do this with generics.

💭 The concept is, instead of declaring a specific data type we use an uppercase letter(or CamelCase identifier). ex, instead x : u8 we use x : T . but we have to inform to the compiler that T is a generic type(can be any type) by adding <T> at first.

Generalizing functions

fn takes_anything<T>(x: T) { // x has type T, T is a generic type
}

fn takes_two_of_the_same_things<T>(x: T, y: T) { // both x and y has same type
}

fn takes_two_things<T, U>(x: T, y: U) { // multiple types
}

Generalizing structs

struct Point<T> {
  x: T,
  y: T,
}

fn main() {
  let point_a = Point { x: 0, y: 0 }; // T is a int type
  let point_b = Point { x: 0.0, y: 0.0 }; // T is a float type
}

// 🔎 When addding an implementation for a generic struct, the type parameters should be declared after the impl as well
// impl<T> Point<T> {

Generalizing enums

⭐️ Above Option and Result types are kind of special generic types which are already defined in Rust’s standard library.

  • An optional value can have either Some value or no value/ None.

  • A result can represent either success/ Ok or failure/ Err

Usages of Option

Usages of Result

📖 The Option type is a way to use Rust’s type system to express the possibility of absence. Result expresses the possibility of error.

🔎 Many useful methods have been implemented around Option and Result types. More information can be found on std::option::Option and std::result::Result pages on Rust doc.

⭐️ Also more practical examples of options & results can be found on Error Handling section in Rust doc.

Last updated