Reputation:
I'm trying to write a little matrix program. Using doublke pointers doesnt work so I figure the easiest way is to have a struct that has the #rows and #columns and a 1d array as the matrix.
But there is some error in the initiation of the matrix as i get: weird values for the indices (0,0) and (0.1) instead of 0.
Something with this perhaps: matrix *mtrx = malloc(sizeof(matrix)); mtrx->m = malloc(r * c * sizeof(int));
matrix.c:
#include <stdio.h>
#include <stdlib.h>
#include "Matrix.h"
matrix *alloc_matrix(int r, int c)
{
matrix *mtrx = malloc(sizeof(matrix));
mtrx->m = malloc(r * c * sizeof(int));
if (mtrx == NULL || m == NULL) {
printf("Out of memory.");
exit(1);
}
mtrx->rows = r;
mtrx->columns = c;
return mtrx;
}
void free_matrix(matrix *mtrx)
{
free(mtrx->m);
free(mtrx);
}
void set(matrix *mtrx, int r, int c, int v)
{
(mtrx->m)[r * mtrx->columns + c] = v;
}
int get(matrix *mtrx, int r, int c)
{
return (mtrx->m)[r * mtrx->columns + c];
}
void print_matrix(matrix *mtrx)
{
int i,j;
printf("\n");
for(i=0; i<mtrx->rows; i++) {
for(j=0; j<mtrx->columns; j++) {
printf("%i ", get(mtrx,i,j));
}
printf("\n");
}
}
matrix.h:
struct matrix_ {
int rows;
int columns;
int *m;
};
typedef struct matrix_ matrix;
matrix *alloc_matrix(int r, int c);
void free_matrix(matrix *mtrx);
void set(matrix *mtrx, int r, int c, int v);
int get(matrix *mtrx, int r, int c);
void print_matrix(matrix *m);
main.c:
#include <stdio.h>
#include <stdlib.h>
#include "Matrix.h"
int main(void)
{
matrix *m = alloc_matrix(3,4);
print_matrix(m);
printf("\nm[0][0] = %i", get(m,0,0));
set(m,0,0,0);
printf("\nm[0][0] = %i", (m->m)[0]);
printf("\nm[0][0] = %i", (m->m)[12]);
return 0;
}
output: all elements except (0,0) and (0,1) is 0.
Upvotes: 3
Views: 1857
Reputation: 106187
malloc
does not zero out allocated memory. If you want to fill the matrix with zeros on allocation, use calloc
instead. In your case, replace:
mtrx->m = malloc(r * c * sizeof(int));
with
mtrx->m = calloc(r*c, sizeof(int));
Answering your follow-up question:
However is there any difference in efficiency between malloc+memset and calloc? or is calloc simplye malloc+memset?
Typically, for "small" allocations calloc
is equivalent to malloc
+ memset
. For "large" allocations (multiple pages, at least), your library may do something more clever relying on some amount of OS support. One approach would be for the OS to lazily zero fill the allocated pages as they are actually used, rather than zero filling all of them immediately upon allocation.
Upvotes: 1
Reputation: 145839
The object allocated by malloc
has an unspecified value. If needed, you have to zero-ize the object yourself (for example using memset
function) or call calloc
instead of malloc
.
Upvotes: 2
Reputation: 2192
That is correct. The C specification does not say arrays are initilized to anything. You just get a piece of memory that will have whatever values there where before.
You can easily initialize to sero though: memset(mtrx->m, 0, sizeof(int) * r * c);
Upvotes: 0
Reputation: 42083
Function malloc allocates a block of memory, returning a pointer to the beginning of the block. It doesn't set all its bits to zero.
Allocating a block of memory and initializing all its bits to zero - that's what calloc function is for.
Or you can explicitly set these bits to zero by using memset
Upvotes: 7
Reputation: 49251
malloc does not initiate with 0's (because of performance issues... it's not always what you want)...
use calloc() instead.
Upvotes: 1
Reputation: 8715
malloc() is not guaranteed to zero the memory. Use calloc() to allocate memory with zeros.
Upvotes: 1