class constexpr expressions in initializer lists

475 views Asked by At

The following code fails to link with g++ 4.8.2:

#include <map>

struct Foo
{
    constexpr static int foo = 1;
};

static std::map<int, int> map {{1, Foo::foo}};

int main()
{
    return Foo::foo;
}

I get the following error:

g++ -std=c++11 -o foo foo.cc
/tmp/ccZXCwiK.o: In function `__static_initialization_and_destruction_0(int, int)':
foo.cc:(.text+0x51): undefined reference to `Foo::foo'

If I comment out the map, things link just fine. Is this a compiler bug, or is it some corner case I am missing in the standard?

1

There are 1 answers

1
Lightness Races in Orbit On BEST ANSWER

You forgot to define the static member.

As soon as you odr-use it, a full definition is required. Yes, even though it has an inline initialiser and, yes, even though it's marked constexpr.

Add:

constexpr int Foo::foo;

Your original code works for me in GCC 4.8.1 via both ideone.com and Coliru, but that's with optimisations turned on (so that constant is likely being supplanted for the symbol in each case). With optimisations off, the error is reproducible.