Control flow

next#

Start the next iteration of the enclosing loop immediately.

next is Perl’s equivalent of C’s continue statement: it abandons the rest of the current iteration’s body and jumps to the loop’s iteration step. If the loop has a continue block, that block runs first, then the controlling expression is re-tested (or the next element is taken for foreach), and execution resumes at the top of the body. With a label, next LABEL targets a specific enclosing loop rather than the innermost one.

Synopsis#

next
next LABEL
next EXPR

What you get back#

Nothing. next is a flow-control operator, not an expression — it unwinds out of the current iteration and therefore never yields a value to its caller. Attempting to use it in a value-producing position (for example as the right-hand side of an assignment inside eval {}, sub {}, or do {}) is a misuse: the surrounding construct never completes normally, so there is no return value to observe.

Loop targeting#

Without a label, next refers to the innermost enclosing loop (while, until, for, foreach, or a bare block, which counts as a one-shot loop). With a label it refers to the named loop, no matter how deeply nested the next sits inside other loops:

OUTER: for my $row (@grid) {
    for my $cell (@$row) {
        next OUTER if $cell eq 'skip-row';
        process($cell);
    }
}

next EXPR, available since Perl 5.18, evaluates EXPR at run time and uses its string value as the label name. Otherwise it behaves exactly like next LABEL:

my $target = pick_label();
next $target;                   # same as: next FOO if $target eq "FOO"

Use the runtime form sparingly — a static next LABEL is easier to read and to verify by eye.

Interaction with continue blocks#

A loop’s continue block runs at the end of every iteration, whether that iteration ended normally or via next. This is the whole point of having a continue block: it groups the bookkeeping that must happen on every pass.

my $i = 0;
LINE: while (my $line = <$fh>) {
    next LINE if $line =~ /^\s*#/;  # skip comments
    process($line);
}
continue {
    $i++;                            # runs even for skipped lines
}

last skips the continue block; next does not. This is the simplest distinguishing property of the two, and the reason continue exists as its own construct rather than being baked into the loop body.

Examples#

Basic while loop — discard comment lines, process the rest:

while (my $line = <$fh>) {
    next if $line =~ /^\s*#/;
    next if $line =~ /^\s*$/;       # blank
    handle($line);
}

foreach with an accumulator — skip entries that fail a predicate:

my $total = 0;
for my $n (@values) {
    next unless defined $n;
    next if $n < 0;
    $total += $n;
}

Nested loops with a label — move on to the next outer row as soon as we spot a sentinel in the inner scan:

ROW: for my $row (@grid) {
    for my $cell (@$row) {
        next ROW if $cell eq 'END';
        count($cell);
    }
}

continue block that always runs, even on next:

my @kept;
ITEM: for my $x (@input) {
    next ITEM if $x->{hidden};
    push @kept, $x;
}
continue {
    log_seen($_);                    # every $x is logged, kept or not
}

Escaping a bare block — a standalone { ... } is a one-shot loop, so next jumps past the remaining statements and out of it:

{
    last_chance() or next;           # bare block: next == fall out
    commit();
}

Edge cases#

  • Illegal inside grep / map / a do { } value block. These constructs are not loops — their block is evaluated for its value, not iterated in the loop-control sense. Using next to exit them is a misuse and is called out explicitly in upstream perlfunc. Use a conditional expression instead:

    my @kept = grep { wanted($_) } @xs;           # not: grep { next unless ... }
    my @mapped = map { transform($_) // () } @ys; # empty list == skip
    
  • Not a return. next cannot deliver a value out of a value-returning block such as eval { }, sub { }, or do { }. If you find yourself reaching for next to leave such a block, you want return, or a conditional that produces the value you need.

  • A bare block is a one-shot loop. { ... } with no while / for prefix is semantically a loop that runs exactly once, so next exits it. This is occasionally useful for early-out patterns, but last is the more common choice because it makes the intent clearer.

  • Unknown label is a fatal error. next NOSUCH dies at run time with Can't "next" outside a loop block when no enclosing loop carries that label.

  • continue runs on next, not on last. This is the usual cause of surprise when refactoring: moving bookkeeping out of the loop body into continue changes behaviour only for last, not for next.

  • Precedence and parsing quirks. Unlike most named operators, next has the same precedence as assignment, and it is exempt from the looks-like-a-function rule. That means next ("foo") . "bar" passes "foobar" to next, not just "foo". Parenthesise defensively when the label name comes from an expression:

    next(($cond ? "A" : "B"));
    
  • Threads, signals, destructors. next unwinds the current iteration’s lexical scope: my variables go out of scope, local values are restored, and DESTROY fires on scope-exit objects, just as if the iteration had ended normally. Pending $SIG{...} handlers are not affected.

Differences from upstream#

Fully compatible with upstream Perl 5.42.

See also#

  • last — exit the enclosing loop entirely, skipping any continue block

  • redo — restart the current iteration without re-testing the condition and without running continue

  • return — the right tool for leaving sub { }, eval { }, or do { } with a value; next cannot do this

  • grep — filter a list; use a conditional expression, not next, to drop elements

  • map — transform a list; return the empty list () from the block to drop an element