0

I have a few lines that compile well on my system but don't compile on a colleagues system. That's why I would like to ask what the go-to solution for the problem would look like. I have to deal with a enum that implicitly defines how much space I have to provide for an std::array. Other parts of the code also make use of FooSize being static. (Optimization)

My current implementation looks like this

enum class FooType
{
    ShortFoo,
    LongFoo
};

// defined in a different file
template <FooType FType>
class FooContainer
{
public:

    static const unsigned int FooSize {(FType == FooType::ShortFoo) ? 32 : 64 };

    std::array<float, FooSize> fooArray;

};

The code seems to create issues on older llvm / clang compilers. 32 and 64 are actually provided via pre processor defines. I could just skip the FooType and use the size as an template argument but I would like to know what the most reliable method of initializing FooSize would be.

max66
  • 65,235
  • 10
  • 71
  • 111
ruhig brauner
  • 943
  • 1
  • 13
  • 35
  • How older clang compilers? They support C++11? (enum classes and `std::array` are C++11 introduced feature). And, please, can you transcribe the exact error? – max66 Mar 29 '17 at 13:13
  • LLVM 5.1, so it's XCode 5.1.1. We use C++11 which is a bit odd. (Wouldn't thing that a compiler complaining about this would support c++11) Error: `in-class initializer for static data member is not a constant expression` – ruhig brauner Mar 29 '17 at 13:15

1 Answers1

1

Your code seems correct to me and compile without problems with my olds g++ (4.9.2) and clang++ (3.5).

But, according the error message, could be that your compiler doesn't correctly support the C++11 declaration/initialization of static data members

I suggest you to try in the following way

template <FooType FType>
class FooContainer
{
public:
    static const unsigned int FooSize;

    std::array<float, FooSize> fooArray;

};

template <FooType FType>
int unsigned const FooContainer<FType>::FooSize
   = ((FType == FooType::ShortFoo) ? 32 : 64);

or (I suppose is better)

template <FooType FType>
class FooContainer
{
public:

    static const unsigned int FooSize {(FType == FooType::ShortFoo) ? 32 : 64 };

    std::array<float, FooSize> fooArray;

};

template <FooType FType>
int unsigned const FooContainer<FType>::FooSize;

You can also try defining FooSize as constexpr instead of const.

Another solution could be transform FooSize in a template parameter

template <FooType FType,
   std::size_t FooSize = (FType == FooType::ShortFoo) ? 32 : 64 >
class FooContainer
{
public:
    std::array<float, FooSize> fooArray;
};
max66
  • 65,235
  • 10
  • 71
  • 111