> For the complete documentation index, see [llms.txt](https://learning-rust.gitbook.io/book/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://learning-rust.gitbook.io/book/beyond-the-basics/structs.md).

# Structs

⭐️ Structs are used to **encapsulate related properties** into one unified datatype.

💡 By convention, the name of the struct starts with a capital letter and follows **CamelCase**.

There are 3 variants of structs,\
1\. **C-like structs**

* one or more comma separated name:value pairs
* brace-enclosed  list
* similar to classes (without it’s methods) in OOP languages
* because fields have names, we can access them through dot notation

1. **Tuple structs**
   * one or more comma separated values
   * parenthesized list like tuples
   * looks like a named tuples
2. **Unit structs**
   * a struct with no members at all
   * it defines a new type but it resembles an empty tuple, ()
   * rarely in use,  useful with generics

⭐️ When regarding OOP in Rust, attributes and methods are placed separately on **structs** and **traits**. Structs contain only attributes, traits contain only methods. They are getting connected via **impls**.

## C-like structs

```rust
// Struct Declaration
struct Color {
    red: u8,
    green: u8,
    blue: u8
}

fn main() {
  // creating an instance
  let black = Color {red: 0, green: 0, blue: 0};

  // accessing it's fields, using dot notation
  println!("Black = rgb({}, {}, {})", black.red, black.green, black.blue); //Black = rgb(0, 0, 0)

  // structs are immutable by default, use `mut` to make it mutable but doesn't support field level mutability
  let mut link_color = Color {red: 0,green: 0,blue: 255};
  link_color.blue = 238;
  println!("Link Color = rgb({}, {}, {})", link_color.red, link_color.green, link_color.blue); //Link Color = rgb(0, 0, 238)

  // copy elements from another instance
  let blue = Color {blue: 255, .. link_color};
  println!("Blue = rgb({}, {}, {})", blue.red, blue.green, blue.blue); //Blue = rgb(0, 0, 255)

  // destructure the instance using a `let` binding, this will not destruct blue instance
  let Color {red: r, green: g, blue: b} = blue;
  println!("Blue = rgb({}, {}, {})", r, g, b); //Blue = rgb(0, 0, 255)

  // creating an instance via functions & accessing it's fields
  let midnightblue = get_midnightblue_color();
  println!("Midnight Blue = rgb({}, {}, {})", midnightblue.red, midnightblue.green, midnightblue.blue); //Midnight Blue = rgb(25, 25, 112)

  // destructure the instance using a `let` binding
  let Color {red: r, green: g, blue: b} = get_midnightblue_color();
  println!("Midnight Blue = rgb({}, {}, {})", r, g, b); //Midnight Blue = rgb(25, 25, 112)
}

fn get_midnightblue_color() -> Color {
    Color {red: 25, green: 25, blue: 112}
}
```

## Tuple structs

⭐️ When a tuple struct has only one element, we call it **new type pattern**. Because it helps to create a new type.

```rust
struct Color (u8, u8, u8);
struct Kilometers(i32);

fn main() {
  // creating an instance
  let black = Color (0, 0, 0);

  // destructure the instance using a `let` binding, this will not destruct black instance
  let Color (r, g, b) = black;
  println!("Black = rgb({}, {}, {})", r, g, b); //black = rgb(0, 0, 0);

  //newtype pattern
  let distance = Kilometers(20);
  // destructure the instance using a `let` binding
  let Kilometers(distance_in_km) = distance;
  println!("The distance: {} km", distance_in_km); //The distance: 20 km
}
```

## Unit structs

This is rarely useful on its own, but in combination with other features, it can become useful.

> [📖](https://doc.rust-lang.org/book/first-edition/structs.html) ex: A library may ask you to create a structure that implements a certain trait to handle events. If you don’t have any data you need to store in the structure, you can create a unit-like struct.

```rust
struct Electron;

fn main() {
  let x = Electron;
}
```
