C++11 Features – Understanding the Purpose of constexpr

c++c++11constexpr

This is more of a philosophical question rather than practical code snippet, but perhaps C++ gurus can enlighten me (and apologies if it's been asked already).

I have been reading Item 15 in Meyers's "Effective Modern C++" book, as well as this thread: implicit constexpr? (plus a reasonable amount of googling). The item goes over usage of constexpr for expressions, namely that it defines functions that can return compile time values given compile time inputs.
Moreover, the StackOverflow thread I referred to shows that some compilers are perfectly capable of figuring out for themselves which function invocation results are known at compile time.

Hence the question: why was constexpr added to the standard as compared to defining when compilers should derive and allow static/compile-time values?

I realise it makes various compile-only (e.g. std::array<T, constexpr>) definitions less predictable, but on the other hand, as per Meyers's book, constexpr is a part of the interface,…, if you remove it, you may cause arbitrarily large amounts of client code to stop compiling.
So, not only having explicit constexpr requires people to remember adding it, it also adds permanent semantics to the interface.

Clarification: This question is not about why constexpr should be used. I appreciate that having an ability to programatically derive compile-time values is very useful, and employed it myself on a number of occasions. It's a question on why it is mandatory in situations where compiler may deduce const-time behaviour on its own.

Clarification no. 2: Here is a code snippet showing that compilers do not deduce that automatically, I've used g++ in this case.

#include <array>

size_t test()
  {
  return 42;
  }

int main()
  {
  auto i = test();
  std::array<int, i> arrayTst;
  arrayTst[1] = 20;
  return arrayTst[1];
  }

std::array declaration fails to compile because I have not defined test() as constexpr, which is of course as per standard. If the standard were different, nothing would have prevented gcc from figuring out independently that test() always returns a constant expression.

This question does not ask "what the standard defines", but rather "why the standard is the way it is"?

Best Answer

Before constexpr the compilers could sometimes figure out a compile time constant and use it. However, the programmer could never know when this would happen.

Afterwards, the programmer is immediately informed if an expression is not a compile time constant and he or she realizes the need to fix it.