Closures in depth
As we know already, closures are a fancier version of functions. They are also first-class functions, which means that they can be put into variables or can be passed as an argument to functions or even returned from a function. But what sets them apart from functions is that they are also aware of the environment they are declared within and can reference any variable from their environment. The way they reference variables from their environment is determined by how the variable is used inside the closure.
A closure, by default, will try to capture the variable in the most flexible way possible. Only when the programmer needs a certain way of capturing the value will they coerce to the programmer's intent. That won't make much sense unless we see different kinds of closures in action. Closures under the hood are anonymous structs that implement three traits that represent how closures access their environment. We will look at the three traits (ordered from least restrictive...