我看过这些,它们没有回答我的问题:
variable-sized object may not be initialized
C compile error: "Variable-sized object may not be initialized"
Error: Variable-sized object may not be initialized. But why?
我正在尝试编写一些相当可移植的c
代码:
int main ()
{
const int foo=13;
int bar[foo]={0};
return 0;
}
使用以下任一项编译为'c'代码时,出现'可变大小对象可能无法初始化'错误:
*海合会第4.3.4条
*arm操作系统-操作系统-gnueabi-gcc 4.4.5
如果我在VS 2008中将其编译为c
,则会得到一个略有不同的error C2057: expected constant expression
我知道,在这里,c
代码编译器没有将const int foo=13;
识别为真正的常量;例如我们可能有
void a(int fool)
{
const int foo=fool;
int bar[foo]={0};
}
我也意识到unlike the gcc compilers,VS 2008编译器没有C99 variable-length arrays的概念,而且微软显然没有提到任何未来的支持。
然而,用gcc或MS编译器编译cpp
代码完全不同/更聪明?!
关于gcc'c'代码编译器,还有 * 我不明白 * 的地方是:
- 由于此代码 * 确实 * 编译,
int main ()
{
int bar[13]={0};
return 0;
}
- 为什么这个代码 * 不 * 编译..
int main()
{
const int foo=13; //cpp compiler knows this really is const !
int bar[foo]={0};
return 0;
}
- 但这段代码能编译吗
int main()
{
const int foo=13;
int bar[foo+1]={0}; //wtF?
return 0;
}
(NB:在最后一种情况下,MSc
代码编译失败;与int bar[foo]={0};
一致)
3条答案
按热度按时间7fyelxc51#
C99 §6.7.8 * 初始化 * 说明如下:
要初始化的实体类型应为未知大小的数组或不是可变长度数组类型的对象类型。
所以你的初始化是无效的。
type a[size]
* 不是 * VLA的唯一方法是size
是一个 * 整型常量表达式 *(参见6.7.5.2节),这里的表达式不是整型常量表达式,所以我们有一个VLA:如果大小不存在,则数组类型为不完整类型。如果大小为 * 而不是表达式,则数组类型为未指定大小的可变长度数组类型,只能在具有函数原型范围的声明中使用,但此类数组仍为完整类型。如果大小为整数常量表达式,且元素类型具有已知的常量大小,数组类型不是可变长度数组类型;否则,数组类型是可变长度数组类型。
第6.6/6节 * 常量表达式 * 将其定义为:
整型常量表达式应具有整型类型,并且只能具有以下操作数:整型常量、枚举常量、字符常量、结果为整型常量的sizeof表达式,以及作为强制转换的立即数操作数的浮点常量。整型常量表达式中的强制转换运算符只能将算术类型转换为整型类型,但作为sizeof运算符操作数的一部分的情况除外。
ccrfmcuu2#
实际上,对于我的gcc(版本4.4.4),最后一个示例
也 * 不 * 编译,正如人们所期望的那样。您可能需要仔细检查您的工具链(以验证您没有在那里的某个地方重新链接现有的.o),然后重试。
如果您发现它真的可以工作,这是我的
gcc -v
输出,也许您可以检测到配置中的差异,这可能会提供一些线索。mi7gmzs63#
Matt已经引用了这个标准,应用于整型变量的**
const
限定符不算作整型常量表达式**。我们可能会问为什么?它看起来和整型常量一样无辜!这 * 可能 * 是因为
const
不是绝对的consts
。你可以通过指针改变它们的值,编译器所能做的,如果它捕捉到这样的赋值,就是抛出一个警告,但不能真正阻止你改变const
的值。PS:不要相信在线编译器,如ideone.com等。这里有一个愚蠢的runtime error,它抛出一个非常简单的C程序。