Enumerations are frequently useful constructs, but carry some overhead when used with bindings. Specifically mapping the integral values to string representations and back and validation of both integral values and strings requires boilerplate, frequently replicated across multiple languages.
https://github.com/apache/arrow/pull/10712 would replace some of the enums defined in arrow/compute/api* with a metaprogramming construct which includes validation, stringification, and parsing from string. The question at hand is: is it too confusing for users of the C++ API to replace familiar enums with anything else? *** For example, one replacement from that PR is /// - `emit_null`: a null in any input results in a null in the output. /// - `skip`: nulls in inputs are skipped. /// - `replace`: nulls in inputs are replaced with the replacement string. struct NullHandlingBehavior : public EnumType<NullHandlingBehavior> { using EnumType::EnumType; static constexpr EnumStrings<3> values() { return {"emit_null", "skip", "replace"}; } static constexpr const char* name() { return "NullHandlingBehavior"; } }; which replaces (not shown: deleted boilerplate for stringification, validation, etc in Python and C++): enum NullHandlingBehavior { /// A null in any input results in a null in the output. EMIT_NULL, /// Nulls in inputs are skipped. SKIP, /// Nulls in inputs are replaced with the replacement string. REPLACE, }; Values from an EnumType are constructed at compile time from a string, so for example we don't lose the ability to write an expressive switch over their values: switch (*null_handling) { case *NullHandlingBehavior("emit_null"): // ... }