Search code examples
carrayspointersparametersimplicit-conversion

Array-notation decay to pointer-notation - only for function parameters?


I'm currently learning about how C functions can accept multidimensional arrays, by following the treatment in the book C primer plus, by Stephen Prata (6th edition).

In the book, the author mentions that function that deal with multidimensional array can be declared as...

void somefunction( int (* pt)[4] );

Alternatively, if (and only if) pt is a formal parameter to a function, you can declare it as follows:

void somefunction( int pt[][4] );

I understand that in C, array passed into a function will decay into a pointer to the corresponding type. So pt in int pt[][4] will decay into int (* pt)[4], which is a pointer to array of 4 ints.

But I don't understand why this behavior only happens 'if (and only if) pt is a formal parameter to a function". What does this mean? Why is this the case?


Solution

  • I think he means that you may not declare an array like this

    int pt[][4];
    

    in a program (except a declaration with external or internal linkage) because it is an incomplete type that is the size of the array is unknown.

    However you may use such a declaration as a parameter declaration

    void somefunction( int pt[][4] );
    

    because the parameter is adjusted by the compiler to pointer of the type

    void somefunction( int ( *pt )[4] );
    

    and pointers are always complete types.

    As result for example these function declarations

    void somefunction( int pt[100][4] );
    void somefunction( int pt[10][4] );
    void somefunction( int pt[][4] );
    

    are equivalent and declare the same one function.

    Below there is an example of declaring an array (when a declaration is not a definition) of incomplete type with external linkage.

    #include <stdio.h>
    
    int pt[2][4];
    
    int main(void) 
    {
        extern int pt[][4];
    
        printf( "sizeof( pt ) = %zu\n", sizeof( pt ) );
    
        return 0;
    }
    

    The program output is

    sizeof( pt ) = 32