Reputation: 41
I'm trying to make a function that initializes a random 2 dimensional square matrix given its variable name and number of rows and columns (n in this case). This code returns a "Segmetation fault" error and I don't know why. I've tried using & in if-else in the function initM, but then returns "error: lvalue required as left operand of assignment"Anyone knows how to make it work?
void initM (int n, int **matrix){
for (int i = 0; i < n; i++){
for (int j = 0; j < n; j++){
if (i == j) matrix[i][j] = 101;
else matrix[i][j] = (rand() % 101);
}
}
}
void main (int argc, char *argv[]){
int n = atoi(argv[1]);
int **matrix = (int **)malloc(n*sizeof(int));
for(int i = 0; i < n; i++) matrix[i] = (int *)malloc(n*sizeof(int));
initM(n, matrix);
for (int i = 0; i < n; i++){
for (int j = 0; j < n; j++){
printf("%d ", matrix[i][j]);
}
printf("\n");
}
for (int i = 0; i < n; i++) free(matrix[i]);
free(matrix);
}
Upvotes: 0
Views: 61
Reputation: 123596
int **matrix = (int **)malloc(n*sizeof(int));
The main problem is that sizeof (int)
is not the same as sizeof (int *)
on your system, so you're not allocating enough space. The above call can be rewritten as
int **matrix = malloc( n * sizeof *matrix );
The cast is unnecessary1, and sizeof *matrix == sizeof (int *)
2.
Similarly, you can allocate each matrix[i]
as
matrix[i] = malloc( n * sizeof *matrix[i] ); // sizeof *matrix[i] == sizeof (int)
You should always check the result of a malloc
, calloc
, or realloc
call. While failures are rare, they can happen:
int **matrix = malloc( n * sizeof *matrix );
if ( matrix )
{
for ( i = 0; i < n; i++ )
{
matrix[i] = malloc( n * sizeof *matrix[i] );
if ( matrix[i] )
// do stuff
}
}
Final nit - main
returns int
, not void
. Unless your compiler specifically documents void main( int, char ** )
as a valid signature, then using it invokes undefined behavior. Your code may run just fine, but there are (admittedly old or oddball) platforms where typing main
as void
leads to problems.
sizeof
is an operator, not a function - parentheses are only necessary if the operand is a type name.
Upvotes: 0
Reputation: 15813
int **matrix = (int **)malloc(n*sizeof(int));
It should be
int **matrix = malloc(n*sizeof(int*));
In your architecture it happens that sizeof(int)
and sizeof(void*)
do not have the same values.
No need to cast the output of malloc, as void* can correctly behave as any other pointer to object.
Upvotes: 1