GNU 编译器与 Visual Studio 在分配的数组上分配了长度常量,在作用域中
GNU Compilers vs. Visual Studio on Arrays Allocated w/ Length Constant w/in a Scope
我知道,如果你在 c/c++ 中设置了一个动态值,你就不能在括号内使用该值来分配数组(这将使它成为所谓的可变长度数组 (VLA),当前C++标准不支持)......
即参见:
C++ : 可变长度数组
http://en.wikipedia.org/wiki/Variable-length_array
不太明白(以及我在这里没有看到确切的问题)是为什么GNU c/c ++编译器(gcc
,g++
)可以使用基于整数值的动态分配(据我所知),只要该值是数组分配范围内的常量,但是Visual Studio
不支持这一点,并且会拒绝编译代码, 吐出错误。
例如在g++
void Foo(const unsigned int bar)
{
double myStuff[bar];
//... do stuff...
}
。编译就好了...
但是相同的代码拒绝在我使用的 VS 版本中编译,除非我传递给 bar 的任何内容在所有范围内都const
,或者是#define
、static const
等。
我怀疑也许 GNU 编译器使用该范围来推断该值是该范围内的常量,并且要么简单地将其分配给 malloc 或以某种方式专门处理它。
我的问题是:
- 谁(VS或GNU)在他们如何方面更接近标准处理这个?
- 有没有办法在范围内使用
[]
值来执行此 VS,但不会在整个程序中全局const
而无需malloc
调用? - 如果我在我的GNU 编译的代码?
从语言的角度来看,VLA 仅在 C 中受支持,并且仅从 C99 开始支持。 它们在C++中不受支持。
从编译器的角度来看,g++ 将支持 VLA 作为 C90 和 C++ 的扩展,但如果使用 -pedantic
进行编译,它将禁用这些扩展,并且会出现编译错误。
Visual Studio在C或C++中根本不支持VLA。 VS最多只支持C89标准,AFAIK MS根本没有计划支持后来的C标准。
就范围而言,这是在C标准中定义的:
6.7.6.2 数组声明符
...
2 如果标识符被声明为具有可变修改的类型,则该标识符应为普通标识符标识符(如 6.2.3 中所定义),没有链接,并且具有块范围或功能原型范围。如果标识符声明为具有静态或线程存储的对象持续时间,它不应具有可变长度数组类型。
VLA 不能static
或文件范围内声明是有技术原因的;具有静态存储持续时间的对象在程序启动时分配并一直保留到程序终止,如果我没记错的话,不能保证对象将以任何特定顺序分配和初始化。 因此,这些项需要在编译时知道它们的大小。
GNU编译器集合支持可变长度数组作为扩展,使用-pedantic
编译,您将看到预期的警告。
#include <iostream>
int main()
{
int foo = 10;
int bar[foo];
}
编译:
g++-4.8 -std=c++11 -O2 -pedantic -pthread main.cpp && ./a.out
main.cpp: In function ‘int main()’:
main.cpp:6:16: warning: ISO C++ forbids variable length array ‘bar’ [-Wvla]
int bar[foo];
^
- 递归模板化函数不能分配给具有常量限定类型"const tt &"的变量"state"
- 如何为静态常量模板化专用整数值分配存储
- 将编译时常量向量转换为堆分配版本
- 对复合分配中的"常量"的混淆
- 传入与在C++中分配常量引用
- 将常量字符* 分配给字符*
- 将 static_cast<int>(-15) 分配给静态常量字符类型变量
- 移动具有常量成员的类的构造和分配
- cpp 数组 - 分配常量索引有效,而非常量索引不起作用
- C++:可以编写忽略常量分配的代码吗?
- C++ - 无法将顶部常量指针分配给另一个非常量指针
- 为什么在将常量 ptr 分配给常量引用时没有收到编译错误?
- 可选参数常量引用重新分配
- C++分配并使用常量作为初始值设定项
- 如何在C++中将常量引用分配给函数中的指针
- 使用函数中的语句数作为内存分配的常量
- 如何在c++中为指针分配常量地址
- 从头文件 c++ 内的常量二维数组行分配常量 1D 数组
- 预期的常量表达式,不能分配常量大小为0的数组
- 不能分配常量大小为0的数组