访问由双指针创建的数组中的维度外部

时间:2015-08-13 10:56:20

标签: c arrays pointers

这是使用双指针定义5 * 3矩阵的正确方法吗?`

 int **M1;
 M1 = (int **)malloc(5 * sizeof(int *));
 for (i=0;i<5;i++)
 {
    M1[i] = (int *)malloc(3 * sizeof(int));
 }`

如果是这样,我如何在代码中分配M1[3][15] = 9仍然没有错误?为什么在分配M1[6][3]=2时会出现分段错误?

我理解了几次这样的初始化之后,我创建了一个5*xx数组,即我无法超越第5行,但我可以为列数分配任何值。我该如何创建一个5 * 3阵列?

2 个答案:

答案 0 :(得分:1)

在你的代码中,你为5个指针分配内存

M1 = (int **)malloc(5 * sizeof(int *));

以后,根据m

的无关值,您尝试访问超出此范围
for (i=0;i<m;i++)

m超出4时,您基本上可以访问超出范围的内存。

更好的分配方式是

int m = 5;
M1 = malloc(m * sizeof(*M1));
if (M1) 
{
 for (i=0;i<5;i++)
 {
    M1[i] = malloc(3 * sizeof(*M1[i]));
 }
}
  

无法超越第5行,但我可以为列数分配任何值

不,你不能。以任何方式,访问超出范围的内存会调用undefined behaviour

答案 1 :(得分:0)

由于Sourav处理了UB案件,我将回答

  

我应该如何创建一个5 * 3阵列?

为什么不依靠自动变量?除非你有令人信服的理由不使用它们,否则

int matrix[5][3];

如果您事先不知道尺寸,并且不喜欢进行双指针操作,请将其展平:

int *m = malloc(sizeof(int) * rows * cols);
// accessing anything from 0 to (rows * cols) - 1 is permitted

// helper to make usage easier
int get_element(int *m, int i, int j, int cols) {
    return m[i * cols + j];
}

OTOH,如果你只是在编译时不知道第一个维度,那么你可以这样做:

typedef int (Int5) [5];   // cols known at complie-time
int rows = 3;
Int5 *r = malloc(rows * sizeof(Int5));
r[0][0] = 1;   // OK
r[0][5] = 2;   // warning: out of bounds access

使用此方法可以获得更多的类型安全性,因为编译器知道建议中的大小。