0

On https://en.cppreference.com/w/cpp/compiler_support, cosnstexpr vector is stated to be supported. enter image description here

But when I wrote

#include <vector>

constexpr std::vector<int> vec{2, 3, 3, 3};
int main()
{
}

and compiles it using -std=gnu++2b flag, it still triggers a error

In file included from /usr/include/c++/12/vector:61,
                 from test.cpp:1:
/usr/include/c++/12/bits/allocator.h:182:50: error: ‘std::vector<int>(std::initializer_list<int>{((const int*)(& const int [4]{2, 3, 3, 3})), 4}, std::allocator<int>())’ is not a constant expression because it refers to a result of ‘operator new’
  182 |           return static_cast<_Tp*>(::operator new(__n * sizeof(_Tp)));
      |                                    ~~~~~~~~~~~~~~^~~~~~~~~~~~~~~~~~~

I don't understand why, can someone help me?

My gcc version gcc version 12.1.0 (Ubuntu 12.1.0-2ubuntu1~22.04)

and __cpp_constexpr == 202110L

Nicol Bolas
  • 449,505
  • 63
  • 781
  • 982
Andy Lee
  • 53
  • 6

1 Answers1

3

std::vector being constexpr-friendly means that it can be used inside a constant expression evaluation. It does not mean that a variable of that type can be declared with constexpr specifier. (Talking about constexpr std::vector in that context is maybe a bit misleading.)

Because std::vector uses dynamic allocation, it still must be destroyed during the evaluation of the constant expression, which is not the case in the initialization of a variable of that type.

What is allowed now is e.g.:

constexpr int some_calculation(int input) {
    std::vector<int> vec;
    // some complicated algorithm using `input`, using `vec` to store e.g. intermediate results
    return /* the result */;
}

constexpr int constant_value = some_calculation(42);
user17732522
  • 53,019
  • 2
  • 56
  • 105