Question. a generic getter function for reflected type
enojoker opened this issue · 1 comments
first of all, thanks for this great library. I'm a bit of a newbie to c++ metaprogramming. Hope my question is clear.
Following your serialization example, I tried to write a getter function that takes a member's name as input for a reflected type. The code below is what I got so far.
It feels a bit awkward for a getter function to iterator through all members to return the value.
I'm thinking about doing some compile time mapping between member variable name and member index so that I can use
static constexpr decltype(auto) get(U&& target) noexcept
from field_descriptor
. But couldn't get it working ...
Just wondering if you were to implement a generic getter function how would you do it?
Many thanks!
struct serializable : refl::attr::usage::field, refl::attr::usage::function
{
};
struct Point
{
float x;
float y;
};
REFL_TYPE(Point, bases<>)
REFL_FIELD(x, serializable()) // here we use serializable only as a maker
REFL_FIELD(y, serializable())
REFL_END
template <typename T, typename fld>
fld get(T& value, const std::string& fld_name )
{
fld res;
// iterate over the members of T
for_each(refl::reflect(value).members, [&](auto member)
{
// is_readable checks if the member is a non-const field
// or a 0-arg const-qualified function marked with property attribute
if constexpr (is_readable(member) && refl::descriptor::has_attribute<serializable>(member))
{
if (strcmp(get_display_name(member), fld_name.c_str()) == 0)
res = member(value);
}
});
return res;
}
int main(){
Point p{1,2};
double p_x = get<decltype(p),double>(p, "x");
std::cout << "x: " << p_x << std::endl;
return 0;
}
some compile time mapping between member variable name
It might not be possible to do this at compile time if the member variable name is not a compile-time constant.
There is refl::runtime::invoke which does what you're attempting to do in your example.