# Closures: Anonymous Functions that Capture Their Environment
Rust closures are anonymous functions you can save in a variable or pass as an argument ot other functions

You create the closure in one plcae and then call the closure elsewhere to evaluate it in a different context.

Unlike functions, closures can capture values form the scope in which they are defined

This will be demonstrated how thee closure features allow for code reuse and behavior customization

## Capturing the Environment with Closures
We will first examine how we can use closures to capture values fomr the environment they are defined in for later use

Here is the scenario that we will use to examine this:

Every so often, our t-shirt company gives away an exclusive, limited-edition shirt to someone on our mailing list as a promotion.

People on the mailing list can optionally add their colour to their profile.

If the persion cohsen for a free shirt has their favourite colour set, they get that colour shirt.

If the persion hasn't specified a favourite colour, they get whatever colour the company currently gas the most of.

There are many ways to implement this.

For example we are going to use an enum called `ShirtColor` that has the varaiants `Red` and `Blue`(we limit the number of colours avaialable for simplicity)

We represent the company's inventory with an `Inventory` struct that has a field named `shirts` that contains a `Vec<ShirtColor>` reperenting the shirt colours currently in stock.

The method `giveaway` defined on `Inventory` gets the optional shirt colour preference of the free shirt winner, and reutnrs the shirt colour the person will get.

Here is the setup
```rust
#[derive(Debug, PartialEq, Copy, Clone)]
enum ShirtColor {
    Red,
    Blue,
}

struct Inventory {
    shirts: Vec<ShirtColor>,
}

impl Inventory {
    fn giveaway(&self, user_preference: Option<ShirtColor>) -> ShirtColor {
        user_preference.unwrap_or_else(|| self.most_stocked())
    }

    fn most_stocked(&self) -> ShirtColor {
        let mut num_red = 0;
        let mut num_blue = 0;

        for color in &self.shirts {
            match color {
                ShirtColor::Red => num_red += 1,
                ShirtColor::Blue => num_blue += 1,
            }
        }
        if num_red > num_blue {
            ShirtColor::Red
        } else {
            ShirtColor::Blue
        }
    }
}

fn main() {
    let store = Inventory {
        shirts: vec![ShirtColor::Blue, ShirtColor::Red, ShirtColor::Blue],
    };

    let user_pref1 = Some(ShirtColor::Red);
    let giveaway1 = store.giveaway(user_pref1);
    println!(
        "The user with preference {:?} gets {:?}",
        user_pref1, giveaway1
    );

    let user_pref2 = None;
    let giveaway2 = store.giveaway(user_pref2);
    println!(
        "The user with preference {:?} gets {:?}",
        user_pref2, giveaway2
    );
}
```
The `store` defined in `main` has two blue shirts and one red shirt remaining to distribute for this limited-edition promotion

We call the `giveaway` method for a user with a preference for a red shirt and a user without any preference.

Once again this code could b implemented in man ways and here, to focus on closures, we are stuck to concepts you already learned except for the body of the `giveaway` method that uses a closure.

In the `giveaway` method, we get the user preference as a paramter of type `Option<ShirtColor>` and call the `unwrap_or_else` method on `user_preference`

The [`unwrap_or_else` method on `Option<T>`](https://doc.rust-lang.org/std/option/enum.Option.html#method.unwrap_or_else) is defined by the std library.

It takes one argument: a closure without any args that returns a value `T` (the same tpe stored in the `Some` variant of the `Option<T>`, in this case `ShirtColor`)

If the `Option<T>` is the `Some` variant `unwrap_or_else` returns the value form within the `Some`.

If the `Option<T>` is the `None` varaint, `unwrap_or_else` calls the closure and returns the value returned by the cloosure.

We specify the closure expression `|| self.most_stocked()` as the argument to `unwrap_or_else`.

This is a closure that takes no paramters itself (if the closure has paramters, they would appear between the two verticalbars).

The body of thee closure calls `self.most_stocked()`

We are defining the closure here and the implementation of `unwrap_or_else` will evaluate the closure later if the result is needed

Here is the output of this code
```
$ cargo run
   Compiling shirt-company v0.1.0 (file:///projects/shirt-company)
    Finished `dev` profile [unoptimized + debuginfo] target(s) in 0.27s
     Running `target/debug/shirt-company`
The user with preference Some(Red) gets Red
The user with preference None gets Blue
```

One aspect to notice is here is that we have passed a closure that calls `self.most_stocked()` on current `Inventory` intance.

The std library didn't need to know anything about te `Inventory` or `ShirtColor` types we defined or the logic we want to use in this scenario.

The closure captures an immutalbe reference to the `self` `Inventory` instance and passes ot woth the code we specify to the `unwrap_or_else` method

Funcions on the other hand are not able to capture their environment in this way.

## Closure Type Inference and Annoation