我正在阅读 P2996 (https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2024/p2996r2.html) 论文,该论文介绍了 C++ 语言中的反射。有一些示例展示了如何使用这些功能。在示例 3.2 中,我们有以下代码:
consteval auto member_number(int n) {
return std::meta::nonstatic_data_members_of(^S)[n];
}
但是在示例 3.14 中有:
std::vector args = {^To, ^From};
for (auto mem : nonstatic_data_members_of(^From)) {
args.push_back(reflect_value(mem));
}
我的问题是为什么我们需要在第二个示例中使用
reflect_value
?当我们必须在一般情况下使用该函数时,我们如何知道 nonstatic_data_members_of
的乘积不够?
在第二个例子中,
mem
是一个 std::meta::info
,反映 From
的非静态数据成员。reflect_value(mem)
是反映 std::meta::info
值的 mem
。 (即,[:reflect_value(mem):] == mem
。)请记住,
substitute
对反射实体进行操作(例如,substitute(^std::tuple, {^int})
是^std::tuple<int>
,而不是^std::tuple<^int>
,无论如何都是无效的)。在示例中,get_struct_to_tuple_helper
想要替换为
template <typename To, typename From, std::meta::info ... members>
constexpr auto struct_to_tuple_helper(From const& from) -> To
因此
substitute
的参数(在 ^To
和 ^From
之后)必须 reflect std::meta::info
值(不仅仅是 be 这样的值),这就需要使用 reflect_value
。
(顺便说一下,
P2996R3中的
reflect_value
似乎更名为reflect_result
,但主要功能没有变化。)