【问题标题】:C++ why accessing dynamic array is used without the asterisk operator?C++ 为什么在没有星号运算符的情况下使用访问动态数组?
【发布时间】:2015-09-01 10:29:07
【问题描述】:

例如:

#include <iostream>
using namespace std;

int main(){
int *a;
a = new int[2];
a[1] = 1;

}

据我了解,在“堆内存”中分配了一个大小为 2 的 int 数组,而指针 a 获取该新创建数组的内存地址。但是,当尝试访问(例如)数组的第二个索引(a[1])时,它只是在没有星号运算符的情况下这样做,我不明白为什么,我习惯于看到存储在一个指针指向的内存地址以*pointername 访问,而不是pointername[value]。 所以我的问题是,为什么我们使用下标运算符来访问一个指向数组的指针,而没有星号运算符?

【问题讨论】:

  • 这在实践中意味着同样的事情,但是在 C++ 中,一个类可以重载 [] 运算符,所以最好使用它(显然 int * 没有)。
  • 访问a[1]不是访问第一个,而是第二个元素,c数组索引是从零开始的。
  • 避免这样的编码。使用 C++11 standard containers,例如std::arraystd::vector
  • 指针a 指向数组的第一个元素 - 它是指向int 的指针。指向int 数组的指针如下所示:int (*ap)[2];。如果你有一个指向数组的指针,你确实必须写(*ap)[1] = 1;

标签: c++ arrays pointers memory dynamic


【解决方案1】:

在 C++ 中,将 operator[] 应用于索引为 i 的指针 p 的语义等价于

*(p + i)

*(i + p)

您可以将其视为语法糖。另请注意,这意味着p[N] 等同于N[p]

【讨论】:

    【解决方案2】:

    a[N] 等于 *(a+N) 如果 a 是一个指针。因此,a[1] 取消引用指针 a+1

    【讨论】:

      【解决方案3】:

      数组是包含多个相同大小元素实例的内存块, 下标运算符只是为原始指针的右元素放置一个偏移量。所以 a[0] 将等于 *a。和 a[1] = *a + 1 * sizeof(element) 所以从某种意义上说你是对的,我们最后确实使用了星号运算符,它只是隐藏在语法糖后面。

      【讨论】:

      • a[1]*(a+1),而不是 *a + 1*sizeof(element)
      • 是的,但是你需要知道增加一个指针会增加它所指向的大小。所以本质上它们是相同的,sizeof 使解释更清楚(imo)
      • 你不需要知道。这些知识是内置在语言中的。 a+1 指向a 的第二个元素,而不是第二个字节。
      【解决方案4】:

      索引运算符对于基元数组有特殊含义:array[index] 等价于*(array+index)。一个副作用是,如果你想混淆你的代码,index[array] 意味着完全相同的东西(当然对于原始类型)。对于原始数组,索引运算符是取消引用的语义糖。

      对于非原始类型,类可以覆盖operator[]。这与语义糖正好相反。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2022-07-27
        • 1970-01-01
        • 2019-06-01
        • 2013-03-12
        • 2013-08-04
        • 2019-04-01
        相关资源
        最近更新 更多