--- name: next signature: 'next LABEL' since: 5.0 status: documented categories: ["Control flow"] --- ```{index} single: next; Perl built-in ``` *[Control flow](../perlfunc-by-category)* # next Start the next iteration of the enclosing loop immediately. `next` is Perl's equivalent of C's [`continue`](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`](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 ```perl 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: ```perl 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`: ```perl 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`](continue) blocks A loop's [`continue`](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`](continue) block: it groups the bookkeeping that must happen on every pass. ```perl 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`](last) skips the [`continue`](continue) block; `next` does not. This is the simplest distinguishing property of the two, and the reason [`continue`](continue) exists as its own construct rather than being baked into the loop body. ## Examples Basic `while` loop — discard comment lines, process the rest: ```perl 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: ```perl 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: ```perl ROW: for my $row (@grid) { for my $cell (@$row) { next ROW if $cell eq 'END'; count($cell); } } ``` [`continue`](continue) block that always runs, even on `next`: ```perl 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: ```perl { last_chance() or next; # bare block: next == fall out commit(); } ``` ## Edge cases - **Illegal inside [`grep`](grep) / [`map`](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: ```perl my @kept = grep { wanted($_) } @xs; # not: grep { next unless ... } my @mapped = map { transform($_) // () } @ys; # empty list == skip ``` - **Not a [`return`](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`](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`](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`](continue) runs on `next`, not on [`last`](last)**. This is the usual cause of surprise when refactoring: moving bookkeeping out of the loop body into [`continue`](continue) changes behaviour only for [`last`](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: ```perl next(($cond ? "A" : "B")); ``` - **Threads, signals, destructors**. `next` unwinds the current iteration's lexical scope: [`my`](my) variables go out of scope, [`local`](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`](last) — exit the enclosing loop entirely, skipping any [`continue`](continue) block - [`redo`](redo) — restart the current iteration without re-testing the condition and without running [`continue`](continue) - [`return`](return) — the right tool for leaving `sub { }`, `eval { }`, or `do { }` with a value; `next` cannot do this - [`grep`](grep) — filter a list; use a conditional expression, not `next`, to drop elements - [`map`](map) — transform a list; return the empty list `()` from the block to drop an element