# Download Attributes

During or after a simulation process, we may want to inspect the values of certain attributes on host side. To do that, we need to download the attribute values from all the devices to the host. The function named `downloadAttribute` on both `Places` and `Agents` is designed for this use case, which takes in the type of the attribute as template argument and the integer tag of the attribute to download. The return type is a `std::vector` of `std::unique_ptr`, where each `std::unique_ptr` instance belongs to one device and the array it points to contains the attribute values on that device. 

Note that we don't need to worry about the Ghost Region for `Places`, the downloaded attribute values will automatically skip these invalid instances. 

Consider a custom 2D `Place` class named `MyPlace`, which contains an attribute named `ATTR`. We can download the attribute values using the following code:

```cpp
const auto attr = places->downloadAttribute<int>(MyPlace::Attribute::ATTR);
// attr has type `std::vector<std::unique_ptr<int[]>>`
```

```{note}
Currently, the design of `downloadAttribute` is definitely not pleasant since the values from different devices are separated. This may be fine for linear topology, but in grid topology, the values managed by each `std::unique_ptr` are not contiguous within the `Places` grid, making it hard for users to traverse all the values in a meaningful order. 

Future direction should consider enhancing this by automatically concatenating these arrays and eventually return a big single contiguous array of the attribute values in a layout that match the `Places` grid.z

Another problem is that the downloaded attribute values for `Agents` do not skip the dead instances, meaning that users have to manually check whether each instance is alive. Future direction should also consider skipping the dead `Agent` instances in the downloaded attribute values. 
```