这个问题在这里已有答案:
所以我要做的是使用指针创建一个二维数组作为矩阵。我将一个双指针放入我的CreateMatrix函数,以及行/列,我动态地将数组分配到它们中。我在其中填写了10个进行测试,结果显示它们已全部分配。但是在main中,当我尝试访问2D数组的任意值时,我会发生段错误。无论它是否发生在函数中,都不应该动态分配存储到堆上,因此它应该工作吗?
void CreateMatrix(int ** matrix, int row, int col){
int i, j;
matrix = (int**)malloc(row* sizeof(int*));
for (i = 0; i < row; i++) {
matrix[i] = (int*)malloc(col* sizeof(int));
for (j = 0 ; j < col; j++) {
matrix[i][j] = 10;
printf("i: %d, j: %d\n", i,j);
printf("%d",matrix[i][j]);
}
}
}
主要:
int ** matrix1;
int m1row, m1col = 5;
CreateMatrix(matrix1, m1row, m1col);
fprintf(stdout,"Testing if got out");
fflush(stdout);
printf("This should be 10 : %d",matrix1[0][0]); //definitely segfaults here
另外,一个问题;有人告诉我,当在C中传递'by reference'时,不仅需要函数定义中的指针,还需要函数调用的变量上的&符号。如果我想通过引用传递矩阵a:CreateMatrix(&a, b, c);
而不是CreateMatrix(a, b, c);
。如果我使用&,我得到一个不兼容错误,说我的参数是一个三指针,当我需要一个双指针。 (理论上这是有意义的,因为你传递了双指针的位置)。然后是&仅用于非指针变量?
在matrix
的CreateMatrix
是指针matrix1
的副本。当您在该函数中指定matrix
时,matrix1
中的main
不受影响。
int** CreateMatrix(int row, int col){
int i, j;
int **matrix = (int**)malloc(row* sizeof(int*));
for (i = 0; i < row; i++) {
matrix[i] = (int*)malloc(col* sizeof(int));
for (j = 0 ; j < col; j++) {
matrix[i][j] = 10;
printf("i: %d, j: %d\n", i,j);
printf("%d",matrix[i][j]);
}
}
return matrix;
}
int main() {
// ...
int **matrix1 = CreateMatrix(row, col);
// ...
return 0;
}
如果你想保持一个void
返回类型,那么拿一个指向int**
指针的指针,并在main
中传递该指针的地址。
void CreateMatrix(int ***matrix, int row, int col){
int i, j;
*matrix = (int**)malloc(row* sizeof(int*));
for (i = 0; i < row; i++) {
(*matrix)[i] = (int*)malloc(col* sizeof(int));
for (j = 0 ; j < col; j++) {
(*matrix)[i][j] = 10;
printf("i: %d, j: %d\n", i,j);
printf("%d", (*matrix)[i][j]);
}
}
}
int main() {
int **matrix1;
CreateMatrix(&matrix1, 10, 10);
printf("This should be 10 : %d",matrix1[0][0]);
return 0;
}
变量驻留在内存中。指针存储具有特定类型的变量的内存地址。 &符号&
给出变量的内存地址。
在这里,&
将地址返回到int**
指针matrix1
,然后传递给CreateMatrix
。请注意,matrix
的参数CreateMatrix
已更改为指向int**
指针的指针。
取消引用指针可以获得指针指向的对象。在这里,当我们分配给*matrix
时,我们正在做的主要是使用matrix1
的内存地址(通过matrix
传递)来获取matrix1
中的CreateMatrix
,并将malloc分配的内存块的开始分配给matrix1
。
在你的原始代码中,matrix
中的CreateMatrix
是指针matrix1
的值的副本(可能是垃圾,因为它没有被初始化)。
当你分配给matrix
时,你没有修改matrix1
,你只是在修改一个局部变量。
您提到的代码几乎没有问题。首先m1row
值没有定义,所以它可能会考虑一些垃圾值,所以赋值如
int m1row = 5, m1col = 5;
其次,你将matrix1
传递给CreateMatrix()
函数并在CreateMatrix()
函数中创建动态数组但是没有将动态分配的地址返回到main()
函数,这会在访问时导致分段错误
printf("This should be 10 : %d",matrix1[0][0]);
同样铸造malloc()
结果不需要像尖头here。
示例代码
int** CreateMatrix(int row, int col){
int i, j;
int **matrix = malloc(row* sizeof(*matrix)); /* no need to cast the malloc result */
for (i = 0; i < row; i++) {
matrix[i] = malloc(col* sizeof(**matrix));
for (j = 0 ; j < col; j++) {
matrix[i][j] = 10;
#if 0
printf("i: %d, j: %d\n", i,j);
printf("%d \n",matrix[i][j]);
#endif
}
}
return matrix; /* return the dynamic array */
}
int main(void){
int m1row = 5, m1col = 5;
int **matrix1 = CreateMatrix(m1row, m1col);
printf("\nThis should be 10 : %d\n",matrix1[0][0]);
return 0;
}
matrix
函数的CreateMatrix
参数在该函数的堆栈上分配,这意味着它是本地的。当您使用malloc分配内存时,局部变量matrix
指向该内存。 main中的matrix
变量没有得到更新,这是因为默认情况下参数是按值传递的。
为了使它工作,你必须将matrix
变量的地址(使用&
运算符)从main
传递给CreateMatrix
,即它的签名应该有int *** matrix
。在函数内部,您必须使用*
运算符更新它。像这样:
*matrix = (int **) malloc (row * sizeof(int *))
另一种选择是从CreateMatrix
函数返回分配的内存。