Arrays

unshift#

Prepend one or more values to the start of an array and return the array’s new length.

unshift is the mirror of push: where push appends at the tail, unshift inserts at the head. The values in LIST are prepended as a group, in the order given, so the first argument of LIST becomes the new element 0, the second becomes element 1, and so on, with the original contents sliding to higher indices.

Synopsis#

unshift @arr, $val
unshift @arr, @more
unshift @arr, $first, $second, $third

What you get back#

The new number of elements in the array, as an integer. This is the same value you would get from scalar @arr after the call.

my @colors = ("red");
my $n = unshift @colors, "blue", "green";   # $n == 3

Most calls discard the return value; it is occasionally useful when you want to prepend and branch on the resulting size in one step.

Examples#

Prepend a single element:

my @animals = ("cat");
unshift @animals, "mouse";
# @animals is now ("mouse", "cat")

Prepend several elements — the order is preserved, not reversed. This is the single most common unshift confusion:

my @a = (10, 20, 30);
unshift @a, 1, 2, 3;
# @a is now (1, 2, 3, 10, 20, 30)
# NOT (3, 2, 1, 10, 20, 30)

If you genuinely want the prepended values reversed, reverse them explicitly:

my @a = (10, 20, 30);
unshift @a, reverse(1, 2, 3);
# @a is now (3, 2, 1, 10, 20, 30)

Prepend a whole array — the elements are spliced in, not the array as a single value:

my @head = ("a", "b");
my @tail = ("c", "d");
unshift @tail, @head;
# @tail is now ("a", "b", "c", "d")

Insert at the front vs. insert at the rear. These two calls produce mirror-image results on the same starting array:

my @x = (2, 3);
push    @x, 4;      # @x is (2, 3, 4)   — 4 goes to the rear
unshift @x, 1;      # @x is (1, 2, 3, 4) — 1 goes to the front

Work on an array through a reference. unshift accepts a dereferenced array on the left:

my $ref = [10, 20, 30];
unshift @$ref, 0;
# $$ref[0] is now 0, @$ref is (0, 10, 20, 30)

The arrow-deref form works the same way; write the deref as its own expression rather than stretching a method chain across the unshift argument:

my @list = @$ref;
unshift @list, -1;

Edge cases#

  • Cost is O(n). Every existing element is shifted up by scalar(LIST) slots, so prepending to a large array is proportionally expensive. If you are building a list by repeated prepending, build it with push and reverse at the end — or build it backwards with indices — instead of unshifting in a loop.

  • List is prepended whole, not reversed. unshift @a, 1, 2, 3 places 1 at index 0, 2 at index 1, 3 at index 2. Readers coming from languages where “push to front” naturally reverses (because each element becomes the new head) often expect the opposite; Perl does not.

  • Empty LIST is a no-op. unshift @arr with nothing after it leaves the array unchanged and returns the current element count.

  • Tied arrays: unshift on a tied array calls the UNSHIFT handler if the package provides one; otherwise it falls back to a sequence of SPLICE or STORE / STORESIZE calls. A tie class that only implements FETCH and STORE can still be unshifted, but every call rewrites every index.

  • Dereferenced array works: unshift @$ref, $x modifies the array referenced by $ref in place. unshift @{ $h{key} }, $x autovivifies $h{key} to an empty array reference if it did not previously exist.

  • Scalar expression on the left is a syntax error. A Perl 5.14 experiment briefly accepted unshift $scalar, ... to mean “treat $scalar as an array reference and prepend”; it was removed in Perl 5.24 and stays removed. Write unshift @$scalar, ....

  • Return value in scalar vs. list context is the same integer. Unlike many builtins, unshift does not behave differently in list context — it always returns the new length.

Differences from upstream#

Fully compatible with upstream Perl 5.42.

See also#

  • push — the other end: append to the tail of the array and return the new length

  • shift — the inverse operation: remove and return the first element

  • pop — symmetric partner to shift, removes from the tail

  • splice — general-purpose insert/remove at an arbitrary position; unshift @a, LIST is equivalent to splice(@a, 0, 0, LIST)

  • reverse — pair with unshift when you do want the prepended values to end up in reverse order

  • List::Util — no dedicated prepend; for head-insert semantics unshift is the idiomatic tool, and List::Util::pairs / List::Util::zip compose with it when you are restructuring list shapes rather than just adding to one