Skip to content

Any

blender::Any (source) is a type-safe container for single values of any copy-constructible type. It is similar to std::any but provides the following two additional features:

  • It has adjustable inline buffer capacity and alignment. std::any typically has a small inline buffer but its size is not guaranteed.
  • It can store additional user-defined type information without increasing the sizeof the Any object.

If any of those features are required, it's benefitial to use blender::Any. Otherwise using std::any is fine as well.

/* Construct empty value. */
Any<> value;

/* Check if there is any value inside. */
bool contains_value = value.has_value();

/* Assign values of different types. Each assignment overwrites the previous one. */
value = 4;
value = "four";
value = 4.0f;

/* Check if a specific type is stored. */
bool is_type = value.is<float>();

/* Access the value with a specific type. */
/* This only works if the stored value actually has the given type. */
float value = value.get<float>();

/* Get a pointer to the value without knowing the type. */
void *value = value.get();

/* Remove the value if there is any. */
value.reset();

Additional Type Information

One of the features of blender::Any is that it can store additional information for each type that is stored. This can be done with fairly low overhead, because Any does type erasure and has to store some type-specific information anyway.

In the example below, the blender::Any knows the size of the stored type.

/* Struct that contains all the information that should be stored for the type. */
struct ExtraSizeInfo {
  size_t size;

  /* Function that constructs the extra info for a given type. */
  template<typename T> static constexpr ExtraSizeInfo get()
  {
    return {sizeof(T)};
  }
};

/* Construct the Any with the integer 5 stored in it. */
Any<ExtraSizeInfo> value = 5;

/* Access the size of the stored type. */
int stored_size = value.extra_info().size; /* = 4 */