#include <iostream>
#include <experimental/meta> // C++26 反射头文件(具体命名空间可能依编译器实现而定)
#include <utility>
// 通用反射打印(支持任意字段数)
template<typename T>
void print_fields(const T& obj) {
// 1. 获取 T 的所有非静态数据成员的数量 N
constexpr auto N = std::meta::nonstatic_data_members_of(
^^T,
std::meta::access_context::unchecked()
).size();
// 2. 打印类型名称和字段数量
std::println(
"Processing object of type: {} ({} fields)",
std::meta::display_string_of(^^T),
N
);
// 3. 定义一个泛型 Lambda(接受编译期模板参数包 Is)
// 并通过传入 std::make_index_sequence<N>{} 立即调用它
[&]<std::size_t... Is>(std::index_sequence<Is...>) {
// 4. C++17 折叠表达式(Fold Expression)结合 逗号运算符
// 它会将包中的每一个索引 Is 展开为独立的执行语句
(
( // 内部小括号 bbb:包裹着一个“定义并立即执行”的内部 Lambda
[&] {
// a. 获取第 Is 个数据成员的反射元数据(也是一个反射对象)
constexpr auto member = std::meta::nonstatic_data_members_of(
^^T,
std::meta::access_context::unchecked()
)[Is];
// b. 获取该成员的标识符名称(例如 "age", "name")
constexpr auto name = std::meta::identifier_of(member);
// c. 使用语法糖构件(Splice)来实际访问 obj 对象的该成员
auto& value = obj.[:member:];
// d. 调用具体的打印函数
print_value(name, value, Is);
}() // 这里的 () 表示立即执行这个内部 Lambda
), // 内部小括号 bbb 结束
... // 逗号折叠表达式的展开符:将以上的行为对 Is... 中的每个元素依次重复
); // 外部小括号 aaa 结束
}(std::make_index_sequence<N>{}); // 传入生成的 0 到 N-1 序列并触发外部 Lambda
}
--
FROM 113.132.10.*