Reputation: 1
I am wondering why I cannot get the value in the function, it always cause segmentation fault... `
void multiply(int M, int N, int K, int **matrixA, int **matrixB, int **matrixC){
for (int i = 0; i < M; i++){
for (int j = 0; j < K; j++){
int sum = 0;
for (int k = 0; k < N; k++){
sum += (*(*(matrixA + j) + k)) * (*(*(matrixB + k) + j));
}
*(*(matrixC + i) + j) = sum;
}
}
}
int main(){
int M, N, K;
scanf("%d%d%d", &M, &N, &K);
int matrixA[M][N];
int matrixB[N][K];
int matrixC[M][K];
for(int i=0; i<M; i++){
for(int j=0; j<N; j++){
scanf("%d", matrixA[i]+j);
}
}
for(int i=0; i<N; i++){
for(int j=0; j<K; j++){
scanf("%d", matrixB[i]+j);
}
}
multiply(M, N, K, (int **)matrixA, (int **)matrixB, (int **)matrixC);
for(int i=0; i<M; i++){
for(int j=0; j<K; j++){
printf("%d ", matrixC[i][j]);
}
printf("\n");
}
return 0;
}
`
I want to print out the result "matrixC", but in the function, it would cause segmentation fault. I have tried several times, and it seems like it would miss the addresses of the pointer under the double pointers.
Upvotes: 0
Views: 248
Reputation: 5830
Change the prototype of the function multiply
to this:
void multiply(int M, int N, int K, int matrixA[M][N], int matrixB[N][K], int matrixC[M][K]);
make your life easier like this (body of function multiply):
for (int i = 0; i < M; i++) { //for each row of matrixA
for (int j = 0; j < K; j++) { //for each column of matrixB
matrixC[i][j] = 0; //set field to zero
for (int k = 0; k < N; k++) { //for each col of A and each row of B
//take the dot product of row i (matrixA) and col j (matrixB)
matrixC[i][j] += matrixA[i][k] * matrixB[k][j];
}
}
}
You have an error in this line
sum += (*(*(matrixA + j) + k)) * (*(*(matrixB + k) + j));
which has been corrected to
matrixA[i][k] //index 'i' not 'j'
The var sum
is not needed, therefore opted out.
Based on your comment below
Consider the following code:
int arr[2][2];
int n=0;
for (int i=0; i < 2; ++i) {
for (int j=0; j < 2; ++j) {
arr[i][j] = ++n;
printf("%p (%d) ", &arr[i][j], arr[i][j]);
}
printf("\n");
}
Possible output:
0x7fff7c729470 (1) 0x7fff7c729474 (2)
0x7fff7c729478 (3) 0x7fff7c72947c (4)
As you can see, nicely packed into consecutive integers (basically one array of ints - but that is not guaranteed).
Now have a look at this:
int **parr = (int**) arr;
for (int i=0; i < 2; ++i) {
for (int j=0; j < 2; ++j) {
printf("%p ", *(parr + i) + j);
}
printf("\n");
}
Possible output:
0x200000001 0x200000005
0x400000003 0x400000007
Now, that looks (dangerously) ugly.
As always: pointer != array. Pointer to pointer means, an address of another address, whereas an array is a consecutive block of a type (you could for example take the address of the first element, which is done if the array decays to a pointer).
You have to give the compiler enough information, e.g.
int (*parr)[2] = arr;
See also: https://en.cppreference.com/w/c/language/array#Multidimensional_arrays
Upvotes: 1