# Using Trait Objects That Allow for Values of Different Types In ch8 we discussed one of the limitation of vectors is that they can store elements of only one type We created a workaround where we defined a `SpreadsheetCell` enum that had variants to hold integers, floats and text. This meant that we could store different types of data in each cell and still have a vector that represented a row of cells. This is a good solution when our interchangeable items are a fixed set of types that we know when our code is compiled. However, sometimes we want our library user to be able to extend the set of types that are valid in a particular situation. To show how we may achieve this, we will create a example graphical user interface (GUI) tool that iterates through a list of items, calling a `draw` method on each one to draw it to the screen. This is a common technique for GUI tools. We will start with creating a library crate called `gui` that contains the structure of a GUI library. This crate might include some types for people to use, such as `Button` or `TextField`. In addition `gui` users will want to create their own types that can be drawn. For example, one programmer might add an `Image` and another programmer might add a `SelectBox` In this example we won't build a fully fledged GUI library, but instead will show how all of the pieces would fit together. At the time of writing the library, we cant know and define all the types other programmers might want to create. We do know that `gui` needs to keep track of many values of different and it needs to call a `draw` method on each of these differently typed values. It doesn't need to know exactly what will happen when we call the `draw` method, just that the value will have that method available for us to call. In a language to do this, we might define a class named `Component` that has a method named `draw` on it. The other classes, such as `Button`, `Image` and `SelectBox`, would inherit form `Component` and thus inherit the `draw` method. Each one would override the `draw` method to define their custom behavior, but the framework could treat all of the types as if they were `Component` instances and call `draw` on them. Due to Rust not having inheritance, we need a different way to structure the `gui` library to allow users to extend it with new types. ## Defining a Trait for Common Behavior In order to implement the behavior we want `gui` to have, we will define a trait named `Draw` that will have one method named `draw`. We then can define a vector that takes a *trait object*. A trait object points to both an instance of a type implementing our specified trait and a table used to look up trait methods on that type at runtime. We create a trait object by specifying some sort of pointer, such as a `&` reference or a `Box` smart pointer, then the `dyn` keyword and then specifying the relevant trait. We will discuss about the reason trait objects must use a pointer in Ch20. We can use trait objects in place of a generic or concrete type. Whenever we use a trait object, Rust's type system will ensure at compile time that any value used in that context will implement the trait object's trait. Due to this we don't need to know all possible types at compile time. We mentioned that in Rust, we refrain from calling structs an enums "objects" to distinguish them from other language's objects. In a struct or enum, the data in the struct fields and the behavior in `impl` blocks are separated, where as in other languages, the data and behavior combined into one concept is often labeled an object. Trait objects *are* more like objects in other languages in the sense that they combine data and behavior. Trait objects still differ form traditional objects in that we can't add data to a trait object. Trait objects aren't as generally useful as objects in other languages: their purpose is to allow abstraction across common behavior. Here is an example of how to define a trait named `Draw` with one method named `draw` ```rust pub trait Draw { fn draw(&self); } ``` This is similar syntax to how we defined traits in Ch10. Next comes some new syntax. Here we define a struct named `Screen` that holds a vector named `components`. This vector is of type `Box`, which is a trait object; it is a stand in for any type inside a `Box` that implements the `Draw` trait. ```rust pub struct Screen { pub components: Vec>, } ``` Now on the `Screen` struct we will define a method named `run` that will call the `draw` method on each of its `components` ```rust impl Screen { pub fn run(&self) { for component in self.components.iter() { component.draw(); } } } ``` This works differently form defining a struct that uses a generic type parameter with trait bounds. A generic type parameter can only be substituted with one concrete type at a time, whereas trait objects allow for multiple concrete types to fill in for the trait object at runtime. For example we could have defined the `Screen` struct using generic type and a trait bound, this is shown here. ```rust pub struct Screen { pub components: Vec, } impl Screen where T: Draw, { pub fn run(&self) { for component in self.components.iter() { component.draw(); } } } ``` This restricts us to a `Screen` instance that has a list components all of type `Button` or all of type `TextField`. If you only ever have homogeneous collections, using generics and trait bounds is preferable because the definitions will be monomerized at compile time to use the concrete types. With the method using trait objects, one `Screen` instance can hold a `Vec` that contains a `Box