[英]POD Template class with optional members
I am looking for a way to optionally include members of a c++ class to generate POD structs.我正在寻找一种方法来选择性地包含 c++ 类的成员以生成 POD 结构。 I found that this works fairly well, but is nonstandard:我发现这工作得很好,但不是标准的:
#include <iostream>
template <int v, int n, int t>
struct Point
{
int vertex[v];
float normal[n];
double texcoord[t];
};
int main()
{
std::cout << (sizeof (Point<0,0,1>)) << std::endl;
std::cout << (sizeof (Point<1,0,1>)) << std::endl;
std::cout << (sizeof (Point<1,1,2>)) << std::endl;
std::cout << (sizeof (Point<0,0,0>)) << std::endl;
return 0;
}
So Point<1,0,0> would only contain a vertex (the int type will actually be a vector3 type in practice), and so on.所以 Point<1,0,0> 只会包含一个顶点(实际上 int 类型实际上是 vector3 类型),依此类推。 The main reason for this is to easily support interleaved arrays for OpenGL.这样做的主要原因是为了轻松支持 OpenGL 的交错数组。
Maybe try something like this:也许尝试这样的事情:
#include <type_traits>
template <unsigned int v, unsigned int n, unsigned int t>
struct Point
{
int data[v + n + t];
template <unsigned int i>
typename std::enable_if<(i < v), int &>::type
vertex() { return data[i]; }
template <unsigned int i>
typename std::enable_if<(i < v + n), int &>::type
normal() { return data[v + i]; }
template <unsigned int i>
typename std::enable_if<(i < v + n + t), int &>::type
texcoord() { return data[v + n + i]; }
};
Usage:用法:
Point<1,1,2> p;
p.vertex<0>() = 50;
std::array<T, 0>
is valid, unlike T[0]
and really is a better solution all around. std::array<T, 0>
是有效的,不像T[0]
并且确实是一个更好的解决方案。 Unfortunately, and since this is only available for C++11, I can't figure out if its Boost namesake boost::array
also has such support.不幸的是,由于这仅适用于 C++11,我不知道它的 Boost 同名boost::array
是否也有这样的支持。
It is also possible to write an array
-like helper yourself.也可以自己编写一个类似array
的助手。
You can do this, but you would need specializations.你可以做到这一点,但你需要专业化。
Edit: Matched with new question requirement of different type per array.编辑:匹配每个数组不同类型的新问题要求。 Made template arguments unsigned though.虽然使模板参数无符号。
template <> struct Point<0, 0, 0> {};
template <unsigned v> struct Point<v, 0, 0> { int vertex[v]; };
template <unsigned n> struct Point<0, n, 0> { float normal[n]; };
template <unsigned t> struct Point<0, 0, t> { double texcoord[t]; };
template <unsigned v, unsigned n> struct Point<v, n, 0> {
int vertex[v];
float normal[n];
};
template <unsigned v, unsigned t> struct Point<v, 0, t> {
int vertex[v];
double texcoord[t];
};
template <unsigned n, unsigned t> struct Point<0, n, t> {
float normal[n];
double texcoord[t];
};
Each specialization leaves out the associated array when its corresponding template parameter has value 0
.当对应的模板参数的值为0
时,每个特化都会省略关联的数组。 For three items as shown, the enumeration of specializations is not overly large, and provides exactly the same syntax for accessing the elements as your original post but using standard C++ constructs.对于所示的三个项目,专门化的枚举并不过分大,并且提供与原始帖子完全相同的访问元素的语法,但使用标准 C++ 构造。
Extending this technique beyond 3 arrays would be cumbersome.将此技术扩展到 3 个阵列之外会很麻烦。 However, it could be managed with a script to generate the specializations for you.但是,可以使用脚本对其进行管理,为您生成专业化。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.