0

This code gives me a seg fault:

#include <stdio.h>
#include <stdlib.h>

void print_static(int n, int m, int tab[][m])
{
    int i,j;
    for(i=0; i<n; i++)
    {
        for(j=0; j<m; j++)
            printf("%d ", tab[i][j]);
        printf("\n");
    }
    printf("\n");
}

void print_dynamic(int n, int m, int **tab)
{
    int i,j;
    for(i=0; i<n; i++)
    {
        for(j=0; j<m; j++)
            printf("%d ", tab[i][j]);
        printf("\n");
    }
    printf("\n");
}

int main()
{
    int n=3, m=3;
    int i,j;

    int tab1[3][3] = {{1,2,5}, {3,4,6}, {7,8,9}};

    print_static(n, m, tab1);
    print_dynamic(n, m, tab1);

    n = 2, m = 4;
    int **tab2 = malloc(sizeof(int*) * n);
    for(i=0; i<n; i++)
        tab2[i] = malloc(sizeof(int) * m);

    tab2[0][0] = 1;
    tab2[0][1] = 2;
    tab2[0][2] = 3;
    tab2[0][3] = 4;
    tab2[1][0] = 5;
    tab2[1][1] = 6;
    tab2[1][2] = 7;
    tab2[1][3] = 8;

    print_static(n, m, tab2);
    print_dynamic(n, m, tab2);

    for(i=0; i<n; i++)
        free(tab2[i]);
    free(tab2);
    tab2 = NULL;

    return 0;
}

I read that the name of the array is the pointer to its first element. If so, this code should work = it should print out elements.

yak
  • 3,770
  • 19
  • 60
  • 111
  • 4
    Array type (*e.g.*, `int tab[][m]`) and pointer type (*e.g.*, `int **tab`) are not the same thing and can't be used interchangeably in this manner. – lurker Jan 06 '14 at 16:07
  • @mbratch: thats the thing I dont get. When I do the same thing with 1-dimensional arrays its correct. Why is that? (So `int tab[]` and `int *tab` are the same thing or not?) – yak Jan 06 '14 at 16:07
  • @mbratch: My `print_dynamic` accepts a pointer, but when I try to pass it my static array, `int tab1[3][3] = {{1,2,5}, {3,4,6}, {7,8,9}};` it gives seg fault. I can't understand why – yak Jan 06 '14 at 16:14
  • See http://stackoverflow.com/questions/7586702/is-2d-array-a-double-pointer – lurker Jan 06 '14 at 16:16
  • @yak: `tab1` decays to an expression of type `int (*)[3]`, which is not the same as `int **`. – John Bode Jan 06 '14 at 17:13

1 Answers1

1

The name of an array is not a pointer to the first element. It is the array, and, in many contexts, an array is automatically converted to a pointer to the first element.

However, this is not the cause of your problem. Even when tab1, which is an array of three arrays of three int, is converted to a pointer to its first element, the result is a pointer to an array of three int. Even though an array is automatically converted to a pointer, a pointer to an array is not converted to a pointer to a pointer, nor is the array pointed to by the pointer converted to a pointer. Thus, after conversion, tab1 is a pointer to an array of three int. But the parameter for print_dynamic is a pointer to a pointer to an int.

These are not the same thing. A pointer to an array of three int points to a place where there are three int objects. A pointer to a pointer to an int points to a place where there is a pointer.

Eric Postpischil
  • 195,579
  • 13
  • 168
  • 312