多维数组作为函数参数的形式
2015-03-24 14:26
295 查看
多维数组作为函数参数的形式
今天在看CSAPP的时候,直接敲入了书中的代码片段(P582),没有多加思考,却出现了段错误coredump,然后再纠结:被调用函数是否可以访问到主函数中的数据,函数中的自动变量存在栈中?最后才知道是函数声明的问题。所以通过这篇文章理清了数组作为参数时如何实践,同时不要忽略编译器给我们的警告。
在main中调用matvec1出现问题:
$vi 2.c
$ gcc 2.c csapp.o -lpthread
2.c: In function ‘main’:
2.c:49:2: warning: passing argument 1 of ‘matvec1’ from incompatible pointer type [enabled by default]
2.c:3:6: note: expected ‘int **’ but argument is of type ‘int (*)[3]’
$ ./a.out
Segmentation fault (core dumped)
在一维数组作为函数参数时,既可以写成数组形式也可以写成指针形式,但是对于多维数组上述形式是错误的,只有第一维可以搞成指针形式,要特别注意。
可以选的形式有:
void func(int (*A)[10])
void func(int A[][10])
此时的程序可以正确执行。
但是,这样的情况就限制了这个函数只能处理的数组的类型,没有弹性,所以最优雅的做法是转为一维数组的逻辑来思考(理解行优先存储)。
func(&A[0][0][0], ....);
void func(int *p, int X, int Y, int Z){
int i, j, k;
// todo
p[i*Y+j*Z+k] = AAA;
//todo
}
所以修改后的用例如下:
今天在看CSAPP的时候,直接敲入了书中的代码片段(P582),没有多加思考,却出现了段错误coredump,然后再纠结:被调用函数是否可以访问到主函数中的数据,函数中的自动变量存在栈中?最后才知道是函数声明的问题。所以通过这篇文章理清了数组作为参数时如何实践,同时不要忽略编译器给我们的警告。
在main中调用matvec1出现问题:
$vi 2.c
$ gcc 2.c csapp.o -lpthread
2.c: In function ‘main’:
2.c:49:2: warning: passing argument 1 of ‘matvec1’ from incompatible pointer type [enabled by default]
2.c:3:6: note: expected ‘int **’ but argument is of type ‘int (*)[3]’
$ ./a.out
Segmentation fault (core dumped)
int *matvec1(int **A, int *x, int n){ int i,j; int *y = Malloc(n * sizeof(int)); for(i=0; i<n ;i++) y[i] = 0; for(i=0; i<n; i++) for(j=0; j<n; j++){ y[i] += A[i][j] * x[j]; } return y; }
在一维数组作为函数参数时,既可以写成数组形式也可以写成指针形式,但是对于多维数组上述形式是错误的,只有第一维可以搞成指针形式,要特别注意。
可以选的形式有:
void func(int (*A)[10])
void func(int A[][10])
此时的程序可以正确执行。
int *matvec2(int A[][3], int *x, int n){ int i,j; int *y = Malloc(n * sizeof(int)); for(i=0; i<n ;i++) y[i] = 0; for(i=0; i<n; i++) for(j=0; j<n; j++){ y[i] += A[i][j] * x[j]; } return y; } int *matvec3(int (*A)[3], int *x, int n){ int i,j; int *y = Malloc(n * sizeof(int)); for(i=0; i<n ;i++) y[i] = 0; for(i=0; i<n; i++) for(j=0; j<n; j++){ y[i] += A[i][j] * x[j]; } return y; }
但是,这样的情况就限制了这个函数只能处理的数组的类型,没有弹性,所以最优雅的做法是转为一维数组的逻辑来思考(理解行优先存储)。
func(&A[0][0][0], ....);
void func(int *p, int X, int Y, int Z){
int i, j, k;
// todo
p[i*Y+j*Z+k] = AAA;
//todo
}
所以修改后的用例如下:
int *matvec4(int *A, int *x, int n){ int i,j; int *y = Malloc(n * sizeof(int)); for(i=0; i<n ;i++) y[i] = 0; for(i=0; i<n; i++) for(j=0; j<n; j++){ y[i] += A[i*n + j] * x[j]; } return y; } int main(){ int A[3][3] = {{1,2,3}, {4,5,6}, {7,8,9}}; int x[3] = {2,3,4}; int i, n = 3; int *y = NULL; //y = matvec3(A, x, n); y = matvec4(&A[0][0], x, 3); printf("Ax = ["); for(i=0; i<n ;i++) printf("%d," , y[i]); printf("]\n"); free(y); return 0; }
相关文章推荐
- 关于作为函数参数的多维数组的声明、定义和调用
- 作为函数参数的多维数组想到的两个问题
- 强化C数组作为函数参数-多维数组的本质
- C++多维数组:存储方式、访问方式和作为函数参数
- 如何将多维数组作为参数传递给函数?(以二维数组为例)
- C++中数组以及多维数组作为函数参数时的一些问题
- C++多维数组:存储方式、访问方式和作为函数参数
- C++ 多维数组作为函数的返回值和参数
- 一维或多维数组作为函数参数的问题
- 函数指针、多维数组作为函数参数
- 实现数组作为函数参数传递,切返回值也是数组
- 数组作为函数的参数时,不能通过sizeof运算符得到该数组的大小
- 数组名作为函数参数以及sizeof用法
- 数组和类作为函数参数
- c++中关于数组作为函数参数并传递数组元素个数的几种有效方法的讨论
- 多维数组做函数参数的退化
- C语言数组名作为函数参数
- 2.关于结构体以及结构体数组作为函数入口参数的方法(学习笔记)
- .NET中,写一个函数找出一个整数数组中,第二大的数(整数数组作为函数参数)
- 找出一个整数数组中,第二大的数(整数数组作为函数参数)