【问题标题】:Arrays with 0 elements包含 0 个元素的数组
【发布时间】:2012-04-20 15:14:05
【问题描述】:

0元素的数组和未分配的指针一样吗?

int arr[0];int* arr;一样吗?

编辑:如果我做了类似的事情怎么办:

int x[0];
int* const arr = x;

我尝试了这段代码并编译了它。据我所知, x 和 arr 都应该指向内存中的相同位置。在这种情况下会有什么不同?

【问题讨论】:

  • 指针总是可以指向新的东西,而数组是静态定义的。

标签: c++ arrays pointers


【解决方案1】:

一点也不。

对于 arr[0],arr 具有明确定义的地址。

在 *arr 的情况下,arr 只是未初始化。

在您的编辑之后,您使用之前定义的数组来初始化 const arr:变量的内容没有区别,但在您将被允许对其执行的操作。

【讨论】:

  • @Dasaru 你试过了吗?那不编译...
  • @Dasaru :通常你可以......但你必须手动将 arr 初始化到给定的内存位置,因为它是 const。看看stackoverflow.com/questions/355258/…
  • 在 C++ 中,长度为零的数组是不合法的,因此该数组将没有明确定义的地址。
  • @bames53 :感谢您的澄清。你有那个信息的来源吗?
  • 它来自 C++ 标准,[dcl.array] 第 8.3.4/1 章。 “如果常量表达式 (5.19) 存在,它应该是一个整数常量表达式,并且它的值应该大于零。” (该标准可以从here 下载。查找论文“n3337”)实际上除了引用之外还有更多内容,但这里不能全部引用。
【解决方案2】:

本地声明的零长度数组在 C++ 中是非法的,因此它与未分配的指针不同。

【讨论】:

    【解决方案3】:

    一个长度为零的数组指向一个特定的地址,即数组的开头。在数组结束后,您将有未定义的数据,在这种情况下,在指向的地址处。

    int arr[0];
    int* ptr;
    
    // arr is a reliable value;
    // *arr is not;
    // ptr is not;
    

    一种有用的方法:http://gcc.gnu.org/onlinedocs/gcc-4.1.2/gcc/Zero-Length.html

    【讨论】:

    • 据我所知,根据标准,这种用法是否真正合法仍然没有达成共识,因为越界的数组访问只是 UB(并且 确实会导致软件中的错误,这不仅仅是一个假设)。
    • @KonradRudolph 在 C90 中,毫无疑问:int arr[0] 是非法的,包括在结构中。很明显,如果数组被声明为int arr[1];,并且您使用索引 2 进行访问,则它是未定义的行为。 C99(但不是 C++),您可以将结构的最终成员声明为 int arr[]; 以支持这种用法(但 int arr[0]; 仍然是一个错误)。
    • @James 啊,就是这样。那么C++呢?我很确定越界数组访问是不合法的,对吗?
    • @KonradRudolph 一般来说,对于基本类型、指针和 C 样式数组,C++ 的意图是与 C 相同。(有一种奇异的架构,C++ 正式禁止,但 C 允许,至少在 C++03 中。这被认为是一个缺陷,并且可能已在 C++11 中修复,尽管我尚未验证。)
    猜你喜欢
    • 2014-05-02
    • 1970-01-01
    • 2023-03-06
    • 2013-09-19
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-12-10
    • 1970-01-01
    相关资源
    最近更新 更多