# Matrix multipliers - using a double pointer instead of an array

• 03-01-2005
collymitch
Matrix multipliers - using a double pointer instead of an array
Hey,
I'm working on an openMP enabled matrix-matrix multiplier that will multiply two matrices, A and B, storing the result in C. I have been told to write it in C, of which I have no experience. Before I even begine to think about the omp options I have a few problems to overcome (actually I have many but these are my worst.)

Prob 1:
I need to use a double pointer to store the matrices instead of the following array based approach. (This is because I will not know what the matrix sizes will be at compile time.)

Code:

`double A[SIZE][SIZE], B[SIZE][SIZE], C[SIZE][SIZE];`
am I on the right track by using:

Code:

`double *a, *b, *c;`
I believe this creates 3 pointers to doubles, but are they only single dimensions?? Do they need to be declared as> double **a ...?

Prob 2:
By using a double pointer I think I will need to use the malloc function to allocate the memory required.

Code:

`a = (double *)malloc(sizeof(double)*m*n);`
where m and n are the matrix dimensions. Is this correct?

I appreciate the help and I am sorry if this has been done before but I couldn't find it.

Thanks,

Colly Mitchell
• 03-02-2005
quzah
You should do a board search for dynamic arrays, or multidimension arrays. Few things:

1) Yes, you'll need a pointer to a pointer to a type:
Code:

`double **matrix;`
2) Yes, you'll need to use malloc, but you don't typecast the return of it.
3) You allocate N pointers first.
Code:

`matrix = malloc( sizeof( double * ) * N );`
4) Using a loop, for each N pointer allocated, allocate M doubles.
Code:

`matrix[ x ] = malloc( sizeof( double ) * M );`
5) You need to free in the reverse order. (Step 4, freeing, step 3 freeing.)

Quzah.
• 03-02-2005
collymitch
Hey thanks,

Ok that helped a bit. I read that an array name is just a pointer to the beginning of the allocated memory space. Does this mean I treat the matrix just as an array?

I know that If i want to access the 2nd row element of the 3rd col in an array I would use
Code:

` matrixArray[1][2]`
but what do i use for a pointer then? is it just the same
Code:

`pointerArray[1][2]`
If I want to call a funt to fill the matrix can i use:
Code:

```void fill_matrix(double **matrix) {   int i, j, n = 0;   for (i=0; i<SIZE; i++)       for (j=0; j<SIZE; j++)         matrix[i][j] = n++; }```
Do I allocate the memory when I create the matrix or when I am ready to fill it? Will this work?

Code:

```double **matrixA, **matrixB, **matrixC; void main(...) { ...   m = num_rows;   n = num_cols;   matrixA = malloc(sizeof(double)*m*n);   matrixB = malloc(sizeof(double)*n);   matrixC = malloc(sizeof(double)*n);   fill_matrix(matrixA); ... }```
I apologise if i've messed it up.

Thanks,

Colly
• 03-02-2005
prog-bman
Quote:

Originally Posted by collymitch
Code:

`void main(...)`

GASP!
http://faq.cprogramming.com/cgi-bin/...&id=1043284376
• 03-02-2005
quzah
No. Read what I wrote. You have to allocate a bunch of pointers to doubles. Each of those pointers represents a row. Then, for each row, you allocate a bunch of doubles. These represent the data in the columns of that row. And yes, you can index it like an array.

Quzah.
• 03-02-2005
VirtualAce
You can also just allocate one large 1D array and access it in 2D. This will come down to using offsets into the array instead of actual 2D arrays - which by the way are only 2D compiler side. In assembly, it's just one huge linear array and by using 2D arrays you are forcing your compiler to re-compute the offset every time you access the array.

If you are not worried about efficiency then have at it, but I stay away from 2D arrays and try to stay away from the multiple indirection that is associated with them. It tends to get rather confusing.
• 03-03-2005
collymitch
Ok....

Yeah the 'void main' bit was a typing mistake - i had called the function something else but changed it to main but forgot to change the rest. I was just trying to show a quick example. Sorry.

So is malloc just like using NEW in java or vb where it does malloc automatically?

I sort of get it but what does the
Code:

`matrix[x] =...`
mean?

Quote:

Using a loop, for each N pointer allocated, allocate M doubles.
Does this leave me with a nested loop then like so:

Code:

`double **matrixA;`
say matrixA has m rows and n cols

Code:

```        for (i=0; i<m_rows; i++)                 //each pointer to double represents each row                 matrixA = malloc( sizeof( double * ) * m_rows );                                                 for (j=0; j<n_cols; j++)                         // for each row allocate doubles for the cols                         matrixA[i][j] = malloc( sizeof( double ) * n_cols );```
This doesn't work as it won't assign the void * type to the double type of the matrixA. So what does the matrix[x] in
Quote:

Code:

`matrix[ x ] = malloc( sizeof( double ) * M );`

mean again??

Thanks for the help, I feel that i'm starting to get somewhere now.

Colm
• 03-03-2005
quzah
Here ya go:
Code:

```/* Create a soon-to-be matrix of doubles, named dmatrix */ double **dmatrix; int row; /* Now we need to allocate N 'rows'. */ dmatrix = malloc( sizeof( double* ) * N ); /* Now, for each row, allocate M actual doubles. */ for( row = 0; row < N; row++ )     dmatrix[ row ] = malloc( sizeof( double ) * M ); /* Now you have a matrix of N rows by M colums worth of doubles. */```
You can now use this as a 2D array in effect.
Code:

`dmatrix[ foo ][ bar ] = 2.3;`
To free what you've allocated, you do those two steps in reverse. You free each row's doubles, then you free the pointers (ie: rows)
Code:

```for( row = 0; row < N; row++ )     free( dmatrix[ row ] ); /* Free this row's doubles. */ free( dmatrix ); /* Free the row holders. */```
Quzah.
• 03-10-2005
collymitch
Hey I've got that set up and working fine now by the way. It was a great help it got my program kicked off and have made a good deal of progress so thanks for your help quzah!

Colm.