3
votes

I'm trying to evaluate this simple expression at compile time using C++11 new constexpr feature:

template <int a, int b>
class Test
{
   static constexpr double c = a / b;
};

But here's what Clang keeps telling me:

Constexpr variable 'c' must be initialized by a constant expression

The weird thing is that the following compiles well:

template <int a, int b>
class Test
{
   static constexpr double c = a / 2.f;
};

Do you guys have any idea on why a/b is not a constant expression, and how could I evaluate this at compile time?

Using Clang compiler with -std=c++1y and -stdlib=libc++

Update

The following example causes the error with the original code:

Test<10,0> test1 ;

while:

Test<10,1> test1 ;

does not.

2
Works with Clang 3.5, and with my install of 3.7. - chris
Unrelated but: You want to divide two integers and store the result as a double. The division result will be an integer, e.g. 1/2 is not 0.5 but 0. Is this really what you had in mind? - usr1234567
@usr1234567 you are right, I forgot the cast in the example. - static_cats
I am retracting my close vote since the OP has clarified the source of the problem this is now reproducible. - Shafik Yaghmour
@chris the OP clarified and it is now clear this failed due to undefined behavior. - Shafik Yaghmour

2 Answers

5
votes

The reason why:

Test<10,0> test1 ;

fails is because you have undefined behavior due to division by zero. This is covered in the draft C++ standard section 5.6 [expr.mul] which says:

If the second operand of / or % is zero the behavior is undefined

and constant expressions specifically exclude undefined behavior. I am not sure what version of clang you are using but the versions I have available online do provide a divide by zero warning (see it live):

note: division by zero
static constexpr double c = a / b;
                              ^
2
votes

Solved. One of the template instance had b=0. Somehow, Clang didn't warn me I was dividing by zero. And +Inf is not a constant expression.