【问题标题】:When using a multi-dimensional array, What is the difference between using the pointer to that array and using actual array name as pointer使用多维数组时,使用指向该数组的指针和使用实际数组名称作为指针有什么区别
【发布时间】:2017-05-23 18:53:51
【问题描述】:

我有这段代码,它使用了一个传递数组指针的函数

#include<stdio.h>
void func(int ptr[][3])
{
     printf("%d %d",*ptr,*ptr+1);
}
void main()
{
    int arr[2][3]={{1,2,3},{4,5,6}};
    int (*ptr)[3]=arr;
    func(ptr);
}

现在,如果我将实际的数组名称传递给函数

#include<stdio.h>
void func(int ptr[][3])
{
     printf("%d %d",*ptr,*ptr+1);
}
void main()
{
    int arr[2][3]={{1,2,3},{4,5,6}};
    int (*ptr)[3]=arr;
    func(arr);
}

上述两个代码都会执行并打印相同的地址。但是,如果多维数组的数组名做同样的工作,那么有一个指针有什么意义呢。 或者它们之间有什么区别?

【问题讨论】:

  • 请选择一种语言。根本不会用 C++ 编写这样的代码。
  • 你想要第二个例子func(ptr); --> func(arr); ?
  • @BLUEPIXY 我想知道它们之间的区别
  • 看来你的第一个代码和第二个代码没有区别。
  • 你的两个程序一模一样

标签: c pointers multidimensional-array


【解决方案1】:

这个:

printf("%d %d",*ptr,*ptr+1);

...没有做我猜你打算做的事。特别是,优先级意味着*ptr+1(*ptr)+1 的含义相同,而我猜你真正想要的是:

*(ptr + 1)

要了解两者之间的真正区别,根本不取消引用指针可能更有意义,而只是打印出地址:

void func1(int *a) { 
    printf("%p %p\n", (void *)a, (void *)(a+1));
}

void func2(int ptr[][3]) { 
    printf("%p %p\n", (void *)ptr, (void *)(ptr+1));
}

int main() { 
    int x[] = {1, 2, 3};
    printf("sizeof int == %d\n\n", (int)sizeof(int));
    func1(x);
    func2(&x);
}

现在让我们看看结果:

sizeof int == 4

0x7ffe3f67ba20 0x7ffe3f67ba24
0x7ffe3f67ba20 0x7ffe3f67ba2c

第一个显示以 f00 和 f04 结尾的地址。如图所示,sizeof(int) == 4,所以我们看到的几乎是我们所期望的——将 1 添加到 int * 会产生一个指向下一个 int 的指针,因此地址增加了 4。

在第二种情况下,地址以a20a2c 结尾,因此我们看到了c(十进制12)的差异。在这种情况下,它不是指向 int 的指针——它是指向三个 int 数组的指针。因此,当我们加一个时,地址会改变一个由三个整数组成的数组的大小,每个整数为 4 个字节(即 3x4 = 12)。

【讨论】:

  • int *x = {1, 2, 3}; --> int *x = (int[]){1, 2, 3};。使用-Wall -Werror 编译;-)
  • @BLUEPIXY:我们只是在研究指针的类型如何影响该指针的数学运算方式。您提到的警告不如当前的月相相关。
  • 您应该阅读编译器警告。 “初始化使指针从整数而不进行强制转换”,“标量初始化程序中的多余元素”。无效的指针用法也是 UB。顺便说一句,我还没有投反对票。
  • 为什么你认为1是一个有效的地址作为指针(指向int)?
  • 为什么你认为一个从未取消引用的指针必须满足任何特定的“有效”定义?但是,为了摆脱这种愚蠢的废话,我对代码进行了完全不相关的编辑。
【解决方案2】:

但是如果多维数组的数组名做同样的工作,那么有一个指针又有什么意义呢。

关键是数组与指针完全不同,当然,你可以有一个指针没有一个数组。

该数组在一个连续的内存区域中保存了许多相同类型的对象。因此,指针与数组对声明产生了(巨大)差异。

获取一个数组的指针只是为了传递它是不必要的,因为这在 C 中会自动发生。它也没有什么坏处。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2018-01-04
    • 2016-12-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多