language: C++11 (gcc-4.7.2)
date: 761 days 20 hours ago
link:
visibility: private
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
#include <tuple>
#include <iostream>
 
template<int I>
struct int_ {};
 
template<const char*& Lit>
struct lit {};
 
template<typename T, typename... Initializers>
struct array {
    static const T data[sizeof...(Initializers)];
 
private:
    template<typename Initializer>
    struct get;
};
 
template<typename T, typename... Inits>
template<const char*& Lit>
struct array<T, Inits...>::get<lit<Lit>> {
    constexpr
    static const char*
    make()
    { return Lit; }
};
 
template<typename T, typename... Inits>
template<int N>
struct array<T, Inits...>::get<int_<N>> {
    constexpr
    static int
    make()
    { return N; }
};
 
template<typename T, typename... Inits>
template<typename... Recurse>
struct array<T, Inits...>::get<std::tuple<Recurse...>> {
    /* can't be constexpr unless T(subinitializers...) is */
    static T
    make()
    { return T { get<Recurse>::make()... }; }
};
 
template<typename T, typename... Initializers>
const T array<T, Initializers...>::data[sizeof...(Initializers)] = { { get<Initializers>::make() }... };
 
class custom {
public:
    custom(int i, int j, const char* s)
    : i(i), j(j), s(s)
    {}
 
    friend
    std::ostream&
    operator<<(std::ostream& os, custom const& c)
    {
        return os
            << "{ " << c.i
            << ", " << c.j
            << ", " << c.s
            << " }";
    };
 
private:
    int i, j;
    std::string s;
};
 
namespace {
 
const char* hello = "Hello";
const char* world = "World!";
 
};
 
int
main() {
    typedef array<custom,
        std::tuple< int_<1>, int_<3>, lit<hello> >,
        std::tuple< int_<2>, int_<4>, lit<world> >
    > array;
    const int size = sizeof array::data / sizeof *array::data;
    for(int i = 0; i != size; ++i) {
        std::cout << array::data[i] << '\n';
    }
}