Is there any overhead for using variable-length arrays?

前端 未结 4 1244
北荒
北荒 2020-11-28 06:22

Is there some overhead of using variable-length arrays? Could the size of array be passed via command line argument at run time? Why is it introduced, compared to automatic

4条回答
  •  忘掉有多难
    2020-11-28 07:02

    There is some run-time overhead with variable-length arrays, but you would have to be working fairly hard to measure it. Note that sizeof(vla) is not a compile-time constant if vla is a variable-length array.

    The size of the array can be passed to a function at run-time. If you choose to take the size from a command line argument and convert that into an integer and pass that to the function at run-time, so be it -- it will work.

    Variable-length arrays are used because the variables are automatically allocated to the correct size and automatically freed on exit from the function. This avoids over-allocating space (allocating enough space for the maximum possible size when you mostly work with minimal sizes), and avoids problems with memory clean up.

    Additionally, with multi-dimensional arrays, AFAIK it behaves more like Fortran - you can dynamically configure all the dimensions, rather than being stuck with fixed sizes for all but the leading dimension of the array.


    Concrete evidence of some run-time overhead for VLA - at least with GCC 4.4.2 on SPARC (Solaris 10).

    Consider the two files below:

    vla.c - using a variable-length array

    #include 
    #include 
    extern size_t identity_matrix(int n, int m);
    
    size_t identity_matrix(int n, int m)
    {
        int vla[n][m];
        int i, j;
        assert(n > 0 && n <= 32);
        assert(m > 0 && m <= 32);
        for (i = 0; i < n; i++)
        {
            for (j = 0; j < m; j++)
            {
                vla[i][j] = 0;
            }
            vla[i][i] = 1;
        }
        return(sizeof(vla));
    }
    

    fla.c - using a fixed-length array

    #include 
    #include 
    extern size_t identity_matrix(int n, int m);
    
    size_t identity_matrix(int n, int m)
    {
        int fla[32][32];
        int i, j;
        assert(n > 0 && n <= 32);
        assert(m > 0 && m <= 32);
        for (i = 0; i < n; i++)
        {
            for (j = 0; j < m; j++)
            {
                fla[i][j] = 0;
            }
            fla[i][i] = 1;
        }
        return(sizeof(fla));
    }
    

    Compilation and object file sizes

    For comparison purposes, the names of the local array are different (vla vs fla), and the dimensions on the array are different when it is declared - otherwise, the files are the same.

    I compiled using:

    $ gcc -O2 -c -std=c99 fla.c vla.c
    

    The object file sizes are somewhat different - as measured both by 'ls' and by 'size':

    $ ls -l fla.o vla.o
    -rw-r--r--   1 jleffler rd          1036 Jan  9 12:13 fla.o
    -rw-r--r--   1 jleffler rd          1176 Jan  9 12:13 vla.o
    $ size fla.o vla.o
    fla.o: 530 + 0 + 0 = 530
    vla.o: 670 + 0 + 0 = 670
    

    I've not done extensive testing to see how much of the overhead is fixed and how much is variable, but there is overhead in using a VLA.

提交回复
热议问题