两次解除引用存储为指针指针的2D数组会导致段错误

时间:2016-11-04 02:23:45

标签: c arrays pointers multidimensional-array

我理解为什么int (*arr2d)[3]是好的,为什么**arr2d作为期望传递2d数组的函数的函数参数是坏的。我知道2d数组衰减到指向数组的指针而不是指向指针的指针。我也知道为什么3(列数)是处理二维数组的函数的必要信息(索引到大于1的维数组的基础指针数学需要数组的大小第一个之后的所有维度。

然而,我不知道seg故障发生的原因。如果一个2d数组可以被解引用两次来检索它的第一个元素,为什么当它被视为指向指针时不是这样?我知道2d数组不等同于指针指针。我想知道为什么我不能解除后者的两次在这种情况下。请考虑以下两个示例。

在第一个中,一个2d数组被传递给一个期望指向指针的函数,当它在所述函数中被解除引用两次时会导致seg错误。

void printFirst(int **arr2d) {
    printf("%d\n",**arr2d);
}
void printFirst_corrected(int (*arr2d)[3]) {
    printf("%d\n",**arr2d);
}
int main(void) {
    int arr[3][3] = {{1,2,3},{4,5,6},{7,8,9}};
    printf("%p\n",arr); // prints some address a0
    printf("%p\n",*arr); // prints the same address a0
    printf("%d\n",**arr); // prints 1
    printFirst_corrected(arr); // works, prints 1
    printFirst(arr); // why does this fail? (seg fault, core dumped)
}

在第二个中,一个2d数组被转换为指向指针然后两次解引用,导致seg错误。

int main(void) {
    int arr[][3] = {{1,2,3},{4,5,6},{7,8,9}};
    int **nums2 = (int**)arr;
    printf("%p\n",arr); // prints some address a0
    printf("%p\n",*arr); // prints the same address a0
    printf("%d\n\n",**arr); // prints 1
    printf("%p\n",nums2); // prints a0
    printf("%p\n",*nums2); // prints 0x200000001
    printf("%d\n",**nums2); // fails, seg fault (core dumped)
}

0 个答案:

没有答案