Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/132.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/164.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 大小为0的数组_C++_C_Arrays_Gcc - Fatal编程技术网

C++ 大小为0的数组

C++ 大小为0的数组,c++,c,arrays,gcc,C++,C,Arrays,Gcc,今天我无意中定义了一个一维大小为0的二维数组,但是我的编译器没有抱怨。我发现以下内容表明,至少在gcc的情况下,这是合法的: 但是,我对这种用法有两个问题: 首先,这被认为是良好的编程实践吗?如果是的话,那么我们什么时候应该在现实世界中使用它呢 其次,我定义的数组是二维的,一维的大小为0。这和一维情况一样吗?比如说, int s[0] int s[0][100] int s[100][0] 它们在内存和编译器中是否都相同 编辑:回复Greg:我使用的编译器是gcc4.4.5。我解决这个问题的

今天我无意中定义了一个一维大小为0的二维数组,但是我的编译器没有抱怨。我发现以下内容表明,至少在gcc的情况下,这是合法的:

但是,我对这种用法有两个问题:

首先,这被认为是良好的编程实践吗?如果是的话,那么我们什么时候应该在现实世界中使用它呢

其次,我定义的数组是二维的,一维的大小为0。这和一维情况一样吗?比如说,

int s[0]
int s[0][100]
int s[100][0]
它们在内存和编译器中是否都相同

编辑:回复Greg:我使用的编译器是gcc4.4.5。我解决这个问题的目的不是依赖于编译器,但是如果有任何编译器特有的怪癖也会有帮助:)

提前谢谢

我在


<> P> >上述示例中,没有分配内存用于<代码> A<代码> B>代码> B/<代码>或<代码> C<代码> >

< P>用GCC编译示例,所有三个代码都有<代码> siSoof 0,因此我假设所有这些都由编译器平等对待。C++中的

< P> >声明一个零长度数组是非法的。因此,当您将代码绑定到特定的编译器扩展时,通常不认为这是一种好的做法。动态大小数组的许多用法最好用容器类代替,例如
std::vector

ISO/IEC 14882:2003 8.3.4/1:

如果存在常数表达式(5.19),则其应为积分常数表达式,且其值应大于零

但是,您可以使用
new[]
动态分配长度为零的数组

ISO/IEC 14882:2003 5.3.4/6:

直接新声明符中的表达式应具有非负值的整数或枚举类型(3.9.1)


你的链接解释了一切。当编译时结构的长度未知时,它们将用作结构中的最后一个字段。如果您尝试在堆栈上或在其他声明中间使用它们,您将最终覆盖下一个元素。

鉴于您在问题中引用了编译器,这将有助于提供有关您所关心的特定编译器的信息。请检查此注释,即使用C++11时,
std::array
类型(但普通数组必须至少有一个元素)。@JimFell并不反对1)这些是重复的,2)另一个问题更流行,但这是大约一年前的事了-我真的很好奇为什么不是相反?这将是一个编译器错误,而不是供应商扩展。C++要求所有对象都必须有至少一个字节的大小,所以它们得到唯一的地址。@ Ben Voigt:GCC明确允许零长度数组,这是一个错误,如原始海报所提供的链接所示。它是一个bug。供应商在接受标准没有定义行为的代码方面有很大的回旋余地,但是当他们接受时,他们仍然需要遵循任何适用的标准规则。该标准要求每个对象都有唯一的地址和严格的正大小。子对象需要一个不同于非父对象的地址。@Ben Voigt:你说得对,但我仍然将其定义为扩展,而不是bug。这就是我的推理:对于数组有1+个元素的每种情况,gcc都遵循标准,为每个对象指定一个不同的地址。对于大小为零的数组,不创建任何对象,也不需要提供地址,因此(在我看来)它不属于标准对数组的描述,成为该语言的有效扩展。换句话说,零大小的数组不是数组,而是其他东西(扩展)。该标准是关于
sizeof
的。“当应用于数组时,结果是数组中的总字节数。这意味着一个由n个元素组成的数组的大小是一个元素大小的n倍。”当你选择扩展标准时,你常常不得不打破某些东西。Charles不明白,你可以动态地分配一个长度为零的数组,你能详细说明一下吗。@Krishna_Oza你可以这样做:
int*x=newint[0]#include <iostream>

int main()
{
    int a[0];
    int b[0][100];
    int c[100][0];

    std::cout << "sizeof(a) = " << sizeof(a) << std::endl;
    std::cout << "sizeof(b) = " << sizeof(b) << std::endl;
    std::cout << "sizeof(c) = " << sizeof(c) << std::endl;

    return 0;
}
sizeof(a) = 0
sizeof(b) = 0
sizeof(c) = 0