Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

C++11: std::max(a,b) in static_assert()?

I noticed, that in [24.4.7] of the last C++-Std Doc N3291 max ist not constexpr:

template<class T> const T& max(const T& a, const T& b);

Therefore, it is not allowed to use it in a static_assert for example. Correct?

static_assert( max(sizeof(int),sizeof(float)) > 4, "bummer" );
like image 729
towi Avatar asked Jul 09 '26 03:07

towi


2 Answers

That is correct.

I imagine the reason is simply that std::max calls T::operator< for an arbitrary type T and for std::max to be constexpr, it would require T::operator< to be constexpr, which is unknown.

like image 83
Peter Alexander Avatar answered Jul 13 '26 18:07

Peter Alexander


This is correct; std::min and std::max are not constexpr, not even in the latest draft of C++14 (N3690), so they cannot be used within constant expressions.

There is no good reason for this, only bad reasons. The most significant bad reason is that the C++ committee is composed of individuals who have a limited amount of time to work on standardization, and no-one has put in the work required to make these functions constexpr yet.

Note N3039, a change to the C++ standard adopted in 2010, that slightly extended the constexpr facility specifically so that function such as min and max could be made constexpr.

You can work around this by defining your own min and max functions:

template<typename T>
constexpr const T &c_min(const T &a, const T &b) {
  return b < a ? b : a;
}
template<typename T, class Compare>
constexpr const T &c_min(const T &a, const T &b, Compare comp) {
  return comp(b, a) ? b : a;
}
template<typename T>
constexpr const T &c_min_impl(const T *a, const T *b) {
  return a + 1 == b ? *a : c_min(*a, c_min_impl(a + 1, b));
}
template<typename T>
constexpr T c_min(std::initializer_list<T> t) {
  return c_min_impl(t.begin(), t.end());
}
// ... and so on
like image 23
Richard Smith Avatar answered Jul 13 '26 17:07

Richard Smith



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!