c++ - 未知自定义结构上的结构化绑定(bind)

标签 c++ variadic-templates c++17 structured-bindings

简短版:

我希望能够将结构转换为元组。至少是类型。在下面的代码中,convertToTuple 函数不起作用,因为可变参数不能用于结构化绑定(bind)(据我所知)。关键行是:auto& [values...] = value;

struct Vec3 {
 float x;
 float y;
 float z;
};
template <typename T>
auto structToTuple(T &value) {
 auto& [values...] = value;  //doesn't work
 return std::make_tuple<decltype(values)...>(values...);
}
Vec3 v;
std::tuple<float, float, float> t = structToTuple(v);

基本上,我需要的是一种将自定义结构的类型转换为元组的方法,该元组包含结构中的所有类型。例如:

struct Ray {Vec3, Vec3} -> std::tuple<
 std::tuple<float, float, float>,
 std::tuple<float, float, float>>;

详细问题:

我想创建一个模板函数,它将一个类型或一个类型列表作为模板参数并生成一个纹理列表,每个纹理包含一个项目。另一个函数可以对纹理列表进行采样并将值打包回一起以返回相同的类型。例如,如果我有一个类型:

std::pair<std::tuple<int, int>, int> value;
std::tuple<Texture<int, int>, Texture<int>> tex = createTexture(value);
std::pair<std::tuple<int, int>, int> thisshouldwork = sample(tex);

上面的代码只是我想做的一个简单的例子,并不是我的实际代码。在这种情况下,将创建 2 个纹理,一个纹理将包含元组中的两个整数,另一个将包含一个 int 类型。我的目的是将纹理处理隐藏在一个接口(interface)后面,我可以在纹理中存储任意值(只要它由一些简单类型组成),我可以将这些值上传到 GPU 以供着色器使用。 只要我只使用 std::tuple 和 std::pair,它就可以工作,因为我可以从中提取类型:

template <typename... Args>
void f(std::tuple<Args...> t);

当模板参数是自定义结构时,我希望能够执行相同的操作。例如:

struct Vec3 {
 float x;
 float y;
 float z;
};
Vec3 v;
Texture<float, float, float> tex = createTexture(v);

struct Ray{
 Vec3 pos;
 Vec3 dir;
};
Ray r;
std::tuple<Texture<float,float,float>, Texture<float,float,float>> tex2 = createTexture(r);

我不相信这甚至可能适用于当前的 C++ 标准,但基于结构化绑定(bind),这似乎是可能的。 我的想法是这样的:

template <typename T>
auto structToTuple(T &value) {
 auto& [values...] = value;
 return std::make_tuple<decltype(values)...>(values...);
}
Vec3 v;
std::tuple<float, float, float> t = structToTuple(v);

就我而言,可变参数仅适用于函数或模板参数。但如果 structToTuple 函数可以工作,那将解决我的问题。

提前感谢大家的帮助!

更新:

我找到了解决我的问题的方法(不是通用解决方案): https://github.com/Dwarfobserver/AggregatesToTuples/blob/master/single_include/aggregates_to_tuples.hpp

这个库的作者定义了一个结构到元组的转换,但它只适用于结构的参数不超过 50 个的情况。这在实践中解决了我的问题,尽管我仍然很好奇是否可以使用任意结构。

最佳答案

您没有了解结构化绑定(bind)旨在为您作为程序员提供的要点。它们旨在作为一种“解压缩”函数返回的多个参数的方式,以便于处理各个参数。参数的数量绝不会是未知的或可变的。

https://en.cppreference.com/w/cpp/language/structured_binding

正如上面评论中提到的,有一个 Reflection TS 正在开发中 ( http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2018/n4746.pdf ),但最多只能提供工具来创建满足您需求的解决方案,而不是开箱即用的解决方案.据我了解,Reflection TS 涵盖静态反射,您可以在其中推断类型的形状和内容,而不是动态反射,在动态反射中您可以动态创建类型。

关于c++ - 未知自定义结构上的结构化绑定(bind),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50900559/

相关文章:

c++ - 使用条件运算符递归计算模板值或函数时出现错误 C1202(堆栈溢出)

c++11 - 错误 E0146 : Too many initializer values C++

c++ - 如何使用 Qt 获取文件的 SHA-1/MD5 校验和?

c++ - 如何将参数的数组初始值设定项迁移到 C++11 中的可变模板参数

c++ - 使用来自外部类的可变参数模板的 args 部分专门化可变参数模板内部类是否合法

c++ - 可变参数模板函数参数的编译错误

c++ - 直接列表初始化的自动规则

c++ - OpenGL + Visual Studio 2017 : rendering window not displayed (was OK with Visual 2010)

c++ - 我可以在 C++ 中使用 [] 运算符来创建虚拟数组吗

c++ - 无符号到有符号的转换,位级别会发生什么?