C++ 错误:"x"不是常量表达式,如何解决?

C++ Error: 'x' is not a constant expression, how to fix?

本文关键字:何解决 解决 表达式 错误 常量 C++      更新时间:2023-10-16

简而言之,这里有一个最小的例子:

struct C {
    const int X = 2;
    int y = 2;
};
void f(C* x) {
    switch(x->y) {
        case x->X: printf("%d", 42); break;
        case 123: printf("foo");
    }
}
int main()
{
    C c;
    f(&c);
    return 0;
}

为什么编译器抱怨error: 'x' is not a constant expression,以及如何修复它?

switch内的Case标签只接受编译时常量表达式。x->X而不是常量表达式;因此不能用作CCD_ 4标记。

if替换switch语句以解决此问题:

if (x->y == x->X) {
    printf("%d", 42);
} else if (x->y == 123) {
    printf("foo");
}

在main中,您声明C的一个实例并将其传递给f。根据f的定义,它不能保证C不会被更改,main也无法验证它。我认为f需要是f(C * const x);

给定的代码(模格式)

struct C
{
    int const x = 2;
    int y = 2;
};

…意思是:

struct C
{
    int const x;
    int y;
    C(): x( 2 ), y( 2 ) {}
};

…即成员由每个构造函数初始化。

您甚至可以在用户定义的构造函数中重写该初始化:

struct S
{
    int const x = 2;
    S(): x( 3 ) {}
};

在这里,在每个实例中x将是3。

所以x不是一个编译时常数。这在很大程度上是一个运行时的事情。因此,它不能用作switch中的case标签,因为case标签必须是编译时已知的值。反过来,因为switch构造被设计为在值范围允许的情况下有效地实现为简单的数组索引(计算跳跃)。


一个简单的解决方法是将相关值定义为编译时常数。作为类内的staticenum值。或者在课堂之外。


另一个可能的解决方案是使用if-else梯形图而不是switch

Case接受常量表达式,如2或'a'。Const只是定义了一个不变的变体。