# Variable-length array

> Mediated Wiki article. Canonical URL: https://mediated.wiki/source/Variable-length_array
> Markdown URL: https://mediated.wiki/source/Variable-length_array.md
> Source: https://en.wikipedia.org/wiki/Variable-length_array
> Source revision: 1327211075
> License: Creative Commons Attribution-ShareAlike 4.0 International (https://creativecommons.org/licenses/by-sa/4.0/)

{{Short description|Type of data structure}}
In [computer programming](/source/computer_programming), a '''variable-length array''' ('''VLA'''), also called '''variable-sized''' or '''runtime-sized''', is an [array data structure](/source/array_data_structure) whose length is determined at [runtime](/source/Execution_(computing)), instead of at [compile time](/source/compile_time).<ref name=cray>{{cite web |url=http://docs.cray.com/books/004-2179-001/html-004-2179-001/z893434830malz.html |title=Variable Length Arrays |url-status=dead |archive-url=https://web.archive.org/web/20180126153326/http://docs.cray.com/books/004-2179-001/html-004-2179-001/z893434830malz.html |archive-date=2018-01-26}}</ref> In the language [C](/source/C_(programming_language)), the VLA is said to have a variably modified [data type](/source/data_type) that depends on a value (see [Dependent type](/source/Dependent_type)).

The main purpose of VLAs is to simplify programming of [numerical algorithms](/source/Numerical_method).{{citation-needed|date=December 2025}}

Programming languages that support VLAs include [Ada](/source/Ada_(programming_language)), [ALGOL 68](/source/ALGOL_68) (for non-flexible rows), [APL](/source/APL_(programming_language)), [C#](/source/C_Sharp_(programming_language)) (as unsafe-mode [stack-allocated](/source/Stack-based_memory_allocation) arrays), [COBOL](/source/COBOL), [Fortran](/source/Fortran) 90, [J](/source/J_(programming_language)), and [Object Pascal](/source/Object_Pascal) (the language used in [Delphi](/source/Delphi_(software)) and [Lazarus](/source/Lazarus_(software)), that uses FPC).  [C99](/source/C99) introduced support for VLAs, although they were subsequently relegated in [C11](/source/C11_(C_standard_revision)) to a conditional feature, which implementations are not required to support;<ref>{{cite web |url=https://gcc.gnu.org/onlinedocs/gcc/Variable-Length.html |title=Variable Length – Using the GNU Compiler Collection (GCC) |publisher=}}</ref><ref>ISO 9899:2011 Programming Languages – C 6.7.6.2&nbsp;4.</ref> on some platforms, VLAs could be implemented formerly with <code>[alloca](/source/alloca)()</code> or similar functions.

Growable arrays (also called [dynamic array](/source/dynamic_array)s) are generally more useful than VLAs because dynamic arrays can do everything VLAs can do, and also support growing the array at run-time. For this reason, many programming languages ([JavaScript](/source/JavaScript), [Java](/source/Java_(programming_language)), [Python](/source/Python_(programming_language)), [R](/source/R_(programming_language)), etc.) only support growable arrays. Even in languages that support variable-length arrays, it's often recommended to avoid using (stack-based) variable-length arrays, and instead use ([heap-based](/source/C_dynamic_memory_allocation)) dynamic arrays.<ref>{{cite web |last=Raymond |first=Eric S. |date=2000 |url=https://tldp.org/HOWTO/Software-Release-Practice-HOWTO/develpractice.html |title=Raymond Software Release Practice Howto: 6. Good development practice |website=The Linux Documentation Project}}</ref>

==Memory==
===Allocation===
* The [GNU Compiler Collection](/source/GNU_Compiler_Collection) (GCC) for C allocates memory for VLAs with [automatic storage duration](/source/Automatic_variable) on the [stack](/source/Stack-based_memory_allocation).<ref>{{cite web |url=https://gcc.gnu.org/onlinedocs/gfortran/Code-Gen-Options.html|title=Code Gen Options - The GNU Fortran Compiler|publisher=}}</ref> This is the faster and more straightforward option compared to heap-allocation, and is used by most compilers.
* VLAs can also be allocated on the [heap](/source/Memory_management) and internally accessed using a pointer to this block.

==Implementation==

===Ada===
The following is the same example in [Ada](/source/Ada_(programming_language)). Ada arrays carry their bounds with them, so there is no need to pass the length to the Process function.
<syntaxhighlight lang="Ada">
type Vals_Type is array (Positive range <>) of Float;

function Read_And_Process (N : Integer) return Float is
   Vals : Vals_Type (1 .. N);
begin
   for I in 1 .. N loop
      Vals (I) := Read_Val;
   end loop;
   return Process (Vals);
end Read_And_Process;
</syntaxhighlight>

===Fortran 90===
The equivalent [Fortran 90](/source/Fortran) function is
<syntaxhighlight lang="fortran">
function read_and_process(n) result(o)
    integer,intent(in)::n
    real::o

    real,dimension(n)::vals
    integer::i

    do i = 1,n
       vals(i) = read_val()
    end do
    o = process(vals)
end function read_and_process
</syntaxhighlight>
when utilizing the Fortran 90 feature of checking procedure interfaces at compile time; on the other hand, if the functions use pre-Fortran 90 call interface, the (external) functions must first be declared, and the array length must be explicitly passed as an argument (as in C):
<syntaxhighlight lang="fortran">
function read_and_process(n) result(o)
    integer,intent(in)::n
    real::o

    real,dimension(n)::vals
    real::read_val, process
    integer::i

    do i = 1,n
       vals(i) = read_val()
    end do
    o = process(vals,n)
end function read_and_process
</syntaxhighlight>

=== C ===
Certain [C](/source/C_(programming_language)) language standards require support for variable-length arrays. Variable-length arrays were never part of the [C++](/source/C%2B%2B) language standard.

The following [C99](/source/C99) function allocates a variable-length array of a specified size, fills it with floating-point values, and then passes it to another function for processing. Because the array is declared as an automatic variable, its lifetime ends when <code>readAndProcess()</code> returns.

<syntaxhighlight lang="c">
float readAndProcess(int n) {
    float vals[n];

    for (int i = 0; i < n; ++i) {
        scanf("%f", &vals[i]);
    }

    return process(n, vals);
}
</syntaxhighlight>

In C99, the length parameter must come before the variable-length array parameter in function calls.<ref name=cray/> In C11, a {{code|__STDC_NO_VLA__}} macro is defined if VLA is not supported.<ref>§ 6.10.8.3 of the C11 standard (n1570.pdf)</ref> The C23 standard makes VLA types mandatory again. Only creation of VLA objects with automatic storage duration is optional.<ref>§ 6.10.9.3 of the C23 standard (n3054.pdf)</ref> GCC had VLA as an extension before C99, one that also extends into its C++ dialect.

[Linus Torvalds](/source/Linus_Torvalds) has expressed his displeasure in the past over VLA usage for arrays with predetermined small sizes because it generates lower quality assembly code.<ref>{{cite mailing list |title=LKML: Linus Torvalds: Re: VLA removal (was Re: [RFC 2/2] lustre: use VLA_SAFE) |url=https://lkml.org/lkml/2018/3/7/621 |first=Linus |last=Torvalds |author-link=Linus Torvalds |date=7 March 2018 |mailing-list=Linux kernel}}</ref> With the Linux 4.20 kernel, the [Linux kernel](/source/Linux_kernel) is effectively VLA-free.<ref>{{cite web |title=The Linux Kernel Is Now VLA-Free: A Win For Security, Less Overhead & Better For Clang - Phoronix |url=https://www.phoronix.com/scan.php?page=news_item&px=Linux-Kills-The-VLA |website=www.phoronix.com |language=en}}</ref>

Although C11 does not explicitly name a size-limit for VLAs, some believe it should have the same maximum size as all other objects, i.e. <code>SIZE_MAX</code> bytes.<ref>§6.5.3.4 and §7.20.3 of the C11 standard (n1570.pdf)</ref> However, this should be understood in the wider context of environment and platform limits, such as the typical stack-guard page size of 4 KiB, which is many orders of magnitude smaller than <code>SIZE_MAX</code>.

It is possible to have VLA object with dynamic storage by using a pointer to an array.

<syntaxhighlight lang="c">
#include <stdio.h>
#include <stdlib.h>

float readAndProcess(int n) {
    float (*vals)[n] = malloc(sizeof(float[n]));

    for (int i = 0; i < n; ++i) {
        scanf("%f", &(*vals)[i]);
    }

    float ret = process(n, *vals);
    
    free(vals);
    
    return ret;
}
</syntaxhighlight>

=== C++ ===
While [C++](/source/C%2B%2B) does not support stack-allocated variable length arrays (unlike C which does), they may be allowed by some compiler extensions such as on [GCC](/source/GNU_Compiler_Collection) and [Clang](/source/Clang). Otherwise, an array is instead heap-allocated, however a collection type such as <code>std::vector</code> is probably better. This is because the existing collection types in C++ automatically use "[resource acquisition is initialization](/source/resource_acquisition_is_initialization)" (RAII), and will automatically de-allocate once going out of scope.

<syntaxhighlight lang="cpp">
int* createIntArray(size_t n) {
    return new int[n];
}

int main(int argc, char* argv[]) {
    int* a = createIntArray(5);
    
    // do something with the array

    delete[] a;
}
</syntaxhighlight>

=== C# ===
The following [C#](/source/C_Sharp_(programming_language)) fragment declares a variable-length array of integers. Before C# version 7.2, a pointer to the array is required, requiring an "unsafe" context. The "unsafe" keyword requires an assembly containing this code to be marked as unsafe.

<syntaxhighlight lang="csharp">
unsafe void DeclareStackBasedArrayUnsafe(int size)
{
    int* p = stackalloc int[size];
    p[0] = 123;
}
</syntaxhighlight>

C# version 7.2 and later allow the array to be allocated without the "unsafe" keyword, through the use of the <code>System.Span<T></code> feature.<ref>{{cite web |url=https://docs.microsoft.com/en-us/dotnet/csharp/language-reference/operators/stackalloc |title=stackalloc operator (C# reference) |date=10 July 2024 |publisher=Microsoft}}</ref>

<syntaxhighlight lang="csharp">
using System;

void DeclareStackBasedArraySafe(int size)
{
    Span<int> a = stackalloc int[size];
    a[0] = 123;
}
</syntaxhighlight>

===COBOL===
The following [COBOL](/source/COBOL) fragment declares a variable-length array of records <code>DEPT-PERSON</code> having a length (number of members) specified by the value of <code>PEOPLE-CNT</code>:
<syntaxhighlight lang="cobolfree">
DATA DIVISION.
WORKING-STORAGE SECTION.
01  DEPT-PEOPLE.
    05  PEOPLE-CNT          PIC S9(4) BINARY.
    05  DEPT-PERSON         OCCURS 0 TO 20 TIMES DEPENDING ON PEOPLE-CNT.
        10  PERSON-NAME     PIC X(20).
        10  PERSON-WAGE     PIC S9(7)V99 PACKED-DECIMAL.
</syntaxhighlight>

The [COBOL](/source/COBOL) VLA, unlike that of other languages mentioned here, is safe because COBOL requires specifying maximum array size. In this example, <code>DEPT-PERSON</code> cannot have more than 20 items, regardless of the value of <code>PEOPLE-CNT</code>.

=== Java ===
[Java](/source/Java_(programming_language)) fixes the size of arrays once they are created, but their size can be determined at runtime.

<syntaxhighlight lang="java">
public class Example {
    public static int[] createIntArray(int size) {
        return new int[size];
    }

    public static void main(String[] args) {
        try {
            String s = IO.readln("Input an integer for an array size: ");
            int size = Integer.parseInt(s);
            int[] a = createArray(size);
            System.out.printf("int[] of size %d created", size);
        } catch (NumberFormatException e) {
            System.err.printf("Invalid integer read: %s%n", e.getMessage());
        }
    }
}
</syntaxhighlight>

=== Object Pascal ===
[Object Pascal](/source/Object_Pascal) dynamic arrays are allocated on the heap.<ref>
Michaël Van Canneyt.
[https://www.freepascal.org/docs-html/ref/refsu14.html#x38-520003.3.1  "Free Pascal Reference guide: Dynamic arrays"].
</ref>

In this language, it is called a dynamic array. The declaration of such a variable is similar to the declaration of a static array, but without specifying its size. The size of the array is given at the time of its use.

<syntaxhighlight lang="delphi">
program CreateDynamicArrayOfNumbers(Size: Integer);
var
  NumberArray: array of LongWord;
begin
  SetLength(NumberArray, Size);
  NumberArray[0] := 2020;
end.
</syntaxhighlight>

Removing the contents of a dynamic array is done by assigning it a size of zero.

<syntaxhighlight lang="delphi">
...
SetLength(NumberArray, 0);
...
</syntaxhighlight>

==References==
{{Reflist}}

Category:Arrays
Category:Programming language comparisons
<!-- Hidden categories below -->
Category:Articles with example Ada code
Category:Articles with example C code
Category:Articles with example C Sharp code
Category:Articles with example Fortran code
Category:Articles with example Pascal code

---
Adapted from the Wikipedia article [Variable-length array](https://en.wikipedia.org/wiki/Variable-length_array) by Wikipedia contributors ([contributor history](https://en.wikipedia.org/wiki/Variable-length_array?action=history)). Available under [Creative Commons Attribution-ShareAlike 4.0 International](https://creativecommons.org/licenses/by-sa/4.0/). Changes may have been made.
