考虑以下代码:
#include <array>
#include <cstddef>
struct A {
std::array<std::size_t, 4> test;
void method() {
std::size_t duptest[test.size()] = {}; // error: variable-sized object may not be initialized
}
};
Godbolt叮当声
在Clang下失败,并在注释中显示错误。我不明白为什么这被认为是VLA,因为test.size
是constexpr
函数。我如何阻止duptest
被解释为VLA?
test
即this->test
,求this.size()
必须先求this->test
。但是this
不是一个常量表达式,所以test.size()
不是一个常量表达式,即使std::array::size
是constexpr
,它不使用test
。因此,这是一个非标准的VLA。
您可以使用std::tuple_size
。
size_t duptest[std::tuple_size<decltype(test)>()] = {};
问题表达式test.size()
相当于this->test.size()
,但this
对象更像是一个运行时结构。特别是,在标准c++中,数组的大小必须是编译时常量(又名常量表达式),而表达式this->test.size()
不是。从expr.const # 2:
表达式
e
是一个核心常量表达式,除非e
的求值符合抽象机的规则,需要计算以下表达式之一:
this
,除非在constexpr函数或constexpr构造函数中作为e
的一部分求值,
现在在您的示例中,this
出现在成员函数method
中,但成员函数method
既不是constexpr,也不是作为表达式this->test.size()
的一部分进行计算。
因此,this->test.size()
不能用来指定数组的大小,因为该表达式不是编译时常量。