There was an answer on stackoverflow (which I can\'t seem to find anymore) which demonstrated how a variadic template can be used in C++11 to create a static array at compil
In C++11 (and especially in C++14), the best way to initialize objects at compile-time is with constexpr constructors, not by playing metagames with the typesystem.
struct MyObject {
int x_, y_;
constexpr MyObject(int x, int y) : x_(x), y_(y) { }
};
const MyObject array[] = { MyObject(1,2), MyObject(3,4) };
You can apply your "generator function" idea here, too, if you really want to:
#include
#if __cplusplus < 201400
template struct integer_sequence { typedef integer_sequence type; };
template struct make_index_sequence;
template struct make_index_sequence<0, II...> : integer_sequence {};
template struct make_index_sequence : make_index_sequence {};
#define HACK(x) typename x::type
#else
#include // the C++14 way of doing things
using std::integer_sequence;
using std::make_index_sequence;
#define HACK(x) x
#endif
struct MyObject {
int x_, y_;
constexpr MyObject(int x, int y) : x_(x), y_(y) { }
};
template
struct GeneratedArrayHelper;
template
struct GeneratedArrayHelper> {
static const T data[N]; // element i is initialized with Func(i)
};
template
const T GeneratedArrayHelper>::data[N] =
{ Func(i)... };
template
struct GeneratedArray :
GeneratedArrayHelper)> {};
constexpr MyObject newObject(int i) { return MyObject(2*i, 2*i+1); }
int main() {
for (const MyObject& m : GeneratedArray::data) {
printf("%d %d\n", m.x_, m.y_);
}
// Output:
// 0 1
// 2 3
// 4 5
// 6 7
// 8 9
}
I don't know why Clang 3.5 and GCC 4.8 insist that I put the HACK() macro in there, but they refuse to compile the code without it. Probably I made some dumb mistake and someone can point it out. Also, I'm not confident that all the consts and constexprs are in the best places.