为什么我不能用非文字值初始化静态变量?

时间:2012-03-26 17:46:59

标签: c static const

我有这段代码:

int foo(void){
    return 1;
}

int main(void){
    static const int x = foo();

    //do stuff
    return 0;
}

但是我得到一个关于用非const值初始化静态变量的错误。我认为这与const说明符有关,但事实并非如此。我结束了删除const关键字并执行此操作:

int foo(void){
    return 1;
}

int main(void){
    static int x = 0;
    if (x == 0) x = foo();

    //do stuff
    return 0;
}

现在,为什么编译器只能延迟static int x变量的初始化直到它被使用,更重要的是,为什么它不能只是把它放在读写部分,只是强制执行它不是在编译时编写的?我想在我的代码中使用const AND static关键字来改进语义,但我并不关心编译器如何处理它,只是让它工作。

我对C标准的理解是错误的吗?或者我的编译器在吸吮?这是MSVC 9.0。

3 个答案:

答案 0 :(得分:8)

C需要它。

来自C标准:

  

(C99,6.7.8p4)“具有静态存储持续时间的对象的初始值设定项中的所有表达式都应是常量表达式或字符串文字。”

请注意,const限定符并不意味着不变,而是只读。 const对象在C中不是常量。

静态对象无法通过非常量值初始化的原因与静态对象的初始化“在程序启动之前”(C99,6.2.4p3)有关

答案 1 :(得分:1)

初始化的值必须在编译或链接时确定。 C没有可以在程序启动时运行的构造函数的概念。

答案 2 :(得分:1)

这个约束来自C标准的第6.7.8 / 4节,所以它不仅仅是你的编译器:

  

具有静态存储持续时间的对象的初始值设定项中的所有表达式都应为常量表达式或字符串文字。

原因在于,与C ++标准不同,C不需要执行环境来为运行前初始化提供入口点(当然不是禁止它;静态初始化的方式和时间(5.1.2)未指定)。