#include <iostream>
#include <tuple>
using namespace std;
template<
typename Callable,
typename Tuple,
size_t... Indexes
>
constexpr void tuple_for_each(Tuple&& t, Callable&& f, std::index_sequence<Indexes...>)
{
// ideone only has C++14 :(
int _[] = {(f(std::get<Indexes>(t)),0)...};
}
template<
typename Callable,
typename... Args,
template<typename...> typename Tuple,
typename Is = std::make_index_sequence<sizeof...(Args)>
>
constexpr void tuple_for_each(Tuple<Args...>&& t, Callable&& f)
{
tuple_for_each(t, f, Is{});
}
template<typename T>
struct ReflectionLayout
{
static constexpr auto GetLayout()
{
return std::make_tuple(
std::make_tuple(
"#Unknown", "Unknown"
)
);
}
};
template<typename T>
struct Reflection
{
static constexpr bool has_reflection_info = false;
static constexpr char const* name{ "Unknown" };
static constexpr auto layout() { return ReflectionLayout<T>::GetLayout(); }
static constexpr bool is_complex{ false };
};
#define REGISTER_REFLECTION_INFO(Class) \
template<> \
struct Reflection<Class> \
{ \
static constexpr bool has_reflection_info = true; \
static constexpr char const* name{ #Class }; \
static constexpr auto layout() { return ReflectionLayout<Class>::GetLayout(); } \
static constexpr bool is_complex{ true }; \
};
#define REGISTER_REFLECTION_LAYOUT(Class) \
template<> \
struct ReflectionLayout<Class> \
{ \
using Type = Class; \
static constexpr auto GetLayout() \
{ \
return std::make_tuple(
#define MEMBER(Name) std::make_tuple(#Name, &Type::Name)
#define END_REFLECTION_LAYOUT(Class) \
); \
} \
}; \
REGISTER_REFLECTION_INFO(Class)
struct namedValue
{
string name;
int x;
};
REGISTER_REFLECTION_LAYOUT(namedValue)
MEMBER(name),
MEMBER(x)
END_REFLECTION_LAYOUT(namedValue)
template<typename T>
void printInfo(T val)
{
tuple_for_each(Reflection<T>::layout(),[&](auto&& x) {
// auto [] is C++17, so we have to do this instead
auto& name = get<0>(x);
auto& ptr = get<1>(x);
cout << name << ": " << val.*ptr << endl;
});
}
int main() {
printInfo(namedValue{"numEggs", 37});
return 0;
}
I2luY2x1ZGUgPGlvc3RyZWFtPgojaW5jbHVkZSA8dHVwbGU+CnVzaW5nIG5hbWVzcGFjZSBzdGQ7Cgp0ZW1wbGF0ZTwKCXR5cGVuYW1lIENhbGxhYmxlLAoJdHlwZW5hbWUgVHVwbGUsCglzaXplX3QuLi4gSW5kZXhlcwo+CmNvbnN0ZXhwciB2b2lkIHR1cGxlX2Zvcl9lYWNoKFR1cGxlJiYgdCwgQ2FsbGFibGUmJiBmLCBzdGQ6OmluZGV4X3NlcXVlbmNlPEluZGV4ZXMuLi4+KQp7CgkvLyBpZGVvbmUgb25seSBoYXMgQysrMTQgOigKCWludCBfW10gPSB7KGYoc3RkOjpnZXQ8SW5kZXhlcz4odCkpLDApLi4ufTsKfQoKdGVtcGxhdGU8Cgl0eXBlbmFtZSBDYWxsYWJsZSwKCXR5cGVuYW1lLi4uIEFyZ3MsCgl0ZW1wbGF0ZTx0eXBlbmFtZS4uLj4gdHlwZW5hbWUgVHVwbGUsCgl0eXBlbmFtZSBJcyA9IHN0ZDo6bWFrZV9pbmRleF9zZXF1ZW5jZTxzaXplb2YuLi4oQXJncyk+Cj4KY29uc3RleHByIHZvaWQgdHVwbGVfZm9yX2VhY2goVHVwbGU8QXJncy4uLj4mJiB0LCBDYWxsYWJsZSYmIGYpCnsKCXR1cGxlX2Zvcl9lYWNoKHQsIGYsIElze30pOwp9Cgp0ZW1wbGF0ZTx0eXBlbmFtZSBUPgpzdHJ1Y3QgUmVmbGVjdGlvbkxheW91dAp7CglzdGF0aWMgY29uc3RleHByIGF1dG8gR2V0TGF5b3V0KCkKCXsKCQlyZXR1cm4gc3RkOjptYWtlX3R1cGxlKAoJCQlzdGQ6Om1ha2VfdHVwbGUoCgkJCQkiI1Vua25vd24iLCAiVW5rbm93biIKCQkJKQoJCSk7Cgl9Cn07Cgp0ZW1wbGF0ZTx0eXBlbmFtZSBUPgpzdHJ1Y3QgUmVmbGVjdGlvbgp7CglzdGF0aWMgY29uc3RleHByIGJvb2wgaGFzX3JlZmxlY3Rpb25faW5mbyA9IGZhbHNlOwoJc3RhdGljIGNvbnN0ZXhwciBjaGFyIGNvbnN0KiBuYW1leyAiVW5rbm93biIgfTsKCXN0YXRpYyBjb25zdGV4cHIgYXV0byBsYXlvdXQoKSB7IHJldHVybiBSZWZsZWN0aW9uTGF5b3V0PFQ+OjpHZXRMYXlvdXQoKTsgfQoJc3RhdGljIGNvbnN0ZXhwciBib29sIGlzX2NvbXBsZXh7IGZhbHNlIH07Cn07CgojZGVmaW5lIFJFR0lTVEVSX1JFRkxFQ1RJT05fSU5GTyhDbGFzcykgXAp0ZW1wbGF0ZTw+IFwKc3RydWN0IFJlZmxlY3Rpb248Q2xhc3M+IFwKeyBcCglzdGF0aWMgY29uc3RleHByIGJvb2wgaGFzX3JlZmxlY3Rpb25faW5mbyA9IHRydWU7IFwKCXN0YXRpYyBjb25zdGV4cHIgY2hhciBjb25zdCogbmFtZXsgI0NsYXNzIH07IFwKCXN0YXRpYyBjb25zdGV4cHIgYXV0byBsYXlvdXQoKSB7IHJldHVybiBSZWZsZWN0aW9uTGF5b3V0PENsYXNzPjo6R2V0TGF5b3V0KCk7IH0gXAoJc3RhdGljIGNvbnN0ZXhwciBib29sIGlzX2NvbXBsZXh7IHRydWUgfTsgXAp9OwoKI2RlZmluZSBSRUdJU1RFUl9SRUZMRUNUSU9OX0xBWU9VVChDbGFzcykgXAp0ZW1wbGF0ZTw+IFwKc3RydWN0IFJlZmxlY3Rpb25MYXlvdXQ8Q2xhc3M+IFwKeyBcCgl1c2luZyBUeXBlID0gQ2xhc3M7IFwKCXN0YXRpYyBjb25zdGV4cHIgYXV0byBHZXRMYXlvdXQoKSBcCgl7IFwKCQlyZXR1cm4gc3RkOjptYWtlX3R1cGxlKAoKI2RlZmluZSBNRU1CRVIoTmFtZSkgc3RkOjptYWtlX3R1cGxlKCNOYW1lLCAmVHlwZTo6TmFtZSkKCiNkZWZpbmUgRU5EX1JFRkxFQ1RJT05fTEFZT1VUKENsYXNzKSBcCgkJKTsgXAoJfSBcCn07IFwKUkVHSVNURVJfUkVGTEVDVElPTl9JTkZPKENsYXNzKQoKc3RydWN0IG5hbWVkVmFsdWUKewoJc3RyaW5nIG5hbWU7CglpbnQgeDsKfTsKUkVHSVNURVJfUkVGTEVDVElPTl9MQVlPVVQobmFtZWRWYWx1ZSkKCU1FTUJFUihuYW1lKSwKCU1FTUJFUih4KQpFTkRfUkVGTEVDVElPTl9MQVlPVVQobmFtZWRWYWx1ZSkKCnRlbXBsYXRlPHR5cGVuYW1lIFQ+CnZvaWQgcHJpbnRJbmZvKFQgdmFsKQp7Cgl0dXBsZV9mb3JfZWFjaChSZWZsZWN0aW9uPFQ+OjpsYXlvdXQoKSxbJl0oYXV0byYmIHgpIHsKCQkvLyBhdXRvIFtdIGlzIEMrKzE3LCBzbyB3ZSBoYXZlIHRvIGRvIHRoaXMgaW5zdGVhZAoJCWF1dG8mIG5hbWUgPSBnZXQ8MD4oeCk7CgkJYXV0byYgcHRyID0gZ2V0PDE+KHgpOwoJCWNvdXQgPDwgbmFtZSA8PCAiOiAiIDw8IHZhbC4qcHRyIDw8IGVuZGw7Cgl9KTsKfQoKaW50IG1haW4oKSB7CglwcmludEluZm8obmFtZWRWYWx1ZXsibnVtRWdncyIsIDM3fSk7CglyZXR1cm4gMDsKfQ==