Frage

Okay, so I was trying to do something clever by initializing a bunch of constexpr static int const arrays at compile-time. Even though the runtime-performance is not at all governed by initializing these arrays, it seemed like a fun little exercise. I wrote a test-setup to see if it was possible, and I ended up being able to do this:

struct Test
{
    constexpr static int const array[10] = Array<int, 10, 0, Increment>::array;
};

constexpr int const Test::array[10];

int main()
{
    cout << Test::array[3] << '\n';
}

Here, Array has a static member called array which contains 10 ints, starting at 0, where the value of each subsequent element is determined by a Template-Metaprogramming functor called Increment (i.e. {0, 1, ..., 9}). As expected, the program prints out the number 3.

Awesome, right? I can just write functors now and initialize arrays will all kinds of funky patterns at compile-time. Next step: un-hardcode the array-size 10 by making Test a class-template like so:

template <size_t Size>
struct Test
{
    constexpr static int const array[Size] = Array<int, Size, 0, Increment>::array;
};

template <size_t Size>
constexpr int const Test<Size>::array[Size];

int main()
{
    cout << Test<10>::array[3] << '\n';
}

However, all of a sudden it doesn't compile anymore with the message:

test.cc:43:72: error: array must be initialized with a brace-enclosed initializer

Why does this happen? Is there a reason that this kind of initialization has become invalid once I turn the class into a class-template, or have I stumbled upon something unimplemented/buggy in GCC?

FYI, I can post the rest of my code (the implementation of Array for example) on request. For now I think this should be enough.

EDIT The error can be reproduced with a different, trivial, implementation of Array to save some space here:

template <size_t Size>
struct Array
{
    constexpr static int const array[Size] = {};
};

template <size_t Size>
struct Test
{
    constexpr static int const array[Size] = Array<Size>::array;
};
War es hilfreich?

Lösung

Following is illegal;

static const int a[10] = {};
static const int b[10] = a; // Illegal

So the bug of gcc is in fact for the non template case.

You may use std::array instead of C-array.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top