PERLSUB(1perl)
๐ฆ PERLSUB(1perl) ๐ฆ
soooo this is the Perl Programmers Reference Guide bestie, and today's main character is perlsub โ the whole entire lore drop on Perl subroutines (user-defined functions) ๐ grab a snack, we're going all the way in โจ
๐ NAME ๐
perlsub โ Perl subroutines (user-defined functions) ๐ซถ
๐ SYNOPSIS ๐
okay so first things first, how do you even declare a subroutine? here's the whole menu, no cap ๐
sub NAME; # A "forward" declaration.
sub NAME(PROTO); # ditto, but with prototypes
sub NAME : ATTRS; # with attributes
sub NAME(PROTO) : ATTRS; # with attributes and prototypes
sub NAME BLOCK # A declaration and a definition.
sub NAME(PROTO) BLOCK # ditto, but with prototypes
sub NAME : ATTRS BLOCK # with attributes
sub NAME(PROTO) : ATTRS BLOCK # with prototypes and attributes
use feature 'signatures';
sub NAME(SIG) BLOCK # with signature
sub NAME :ATTRS (SIG) BLOCK # with signature, attributes
sub NAME :prototype(PROTO) (SIG) BLOCK # with signature, prototype
and if you wanna define an anonymous subroutine at runtime (iykyk, the sneaky little sub with no name ๐ง):
$subref = sub BLOCK; # no proto
$subref = sub (PROTO) BLOCK; # with proto
$subref = sub : ATTRS BLOCK; # with attributes
$subref = sub (PROTO) : ATTRS BLOCK; # with proto and attributes
use feature 'signatures';
$subref = sub (SIG) BLOCK; # with signature
$subref = sub : ATTRS(SIG) BLOCK; # with signature, attributes
to import subroutines from somewhere else, you do this ๐ธ:
use MODULE qw(NAME1 NAME2 NAME3);
and to actually call the lil guys ๐ :
NAME(LIST); # Regular subroutine call.
NAME LIST; # Parentheses optional if predeclared/imported.
&NAME(LIST); # Circumvent prototypes.
&NAME; # Makes current @_ visible to called subroutine.
๐ DESCRIPTION ๐
okay so like many languages, Perl lets you define your own subroutines. and bestie, they can live anywhere ๐ฆ โ right there in the main program, pulled in from other files via the do, require, or use keywords, or literally generated on the fly with eval or anonymous subroutines. you can even call a function indirectly using a variable that holds its name, or a CODE reference. main character energy fr.
Perl's whole model for function calls and return values is genuinely so simple it's iconic: every function gets passed, as parameters, one single flat list of scalars. and every function returns, to its caller, one single flat list of scalars. periodt. any arrays or hashes sitting in those call and return lists will collapse, losing their identities ๐ญ โ but you can always use pass-by-reference instead to dodge that entirely. both the call list and the return list can hold as many or as few scalar elements as you want. (also, a function with no explicit return statement often gets called a "subroutine," but honestly from Perl's perspective there's really no difference ๐)
now, in a subroutine that uses signatures (peep the "Signatures" section further down ๐), the arguments get assigned into lexical variables that the signature introduces. in the current implementation of Perl, those arguments are also accessible in the @_ array, in exactly the same way as for non-signature subroutines โ but accessing them that way is now discouraged inside a signature-using subroutine, so like, don't ๐.
in a subroutine that does not use signatures, whatever arguments you pass in show up in the array @_. so if you called a function with two arguments, they'd be chillin' in $_[0] and $_[1]. the array @_ is a local array, but its elements are aliases for the actual scalar parameters ๐. specifically: if an element like $_[0] gets updated, the corresponding argument gets updated too (or you get an error if that thing isn't updatable). and if an argument is an array or hash element that didn't exist at call time, that element only gets created when โ and if โ it's modified, or a reference to it is taken. (some earlier versions of Perl created the element whether or not it was ever assigned to. different era bestie.) assigning to the whole array @_ removes that aliasing, and does not update any arguments โ ๏ธ.
when you're not using signatures, Perl doesn't otherwise give you a way to make named formal parameters. in practice, all you do is assign to a my() list of them. variables that aren't declared to be private are just... global variables, bestie. for the gory details on making private variables, see "Private Variables via my()" and "Temporary Values via local()". and if you wanna build protected environments for a whole set of functions in a separate package (and probably a separate file), see "Packages" in perlmod ๐.
a return statement can be used to exit a subroutine, and you can optionally give it the value to return โ that value gets evaluated in the appropriate context (list, scalar, or void) depending on the context of the subroutine call. if you specify no return value, the subroutine returns an empty list in list context, the undefined value in scalar context, or nothing in void context. and if you return one or more aggregates (arrays and hashes), they all get flattened together into one big indistinguishable list ๐ญ that's just how it is.
if no return is found and the last statement is an expression, its value is returned ๐. but if that last statement is a loop control structure like a foreach or a while, then the returned value is unspecified (read: do not trust it, do not look at it, do not perceive it). the empty sub returns the empty list ๐ธ.
Example:
sub max {
my $max = shift(@_);
foreach $foo (@_) {
$max = $foo if $max < $foo;
}
return $max;
}
$bestday = max($mon,$tue,$wed,$thu,$fri);
Example:
# get a line, combining continuation lines
# that start with whitespace
sub get_line {
$thisline = $lookahead; # global variables!
LINE: while (defined($lookahead = <STDIN>)) {
if ($lookahead =~ /^[ \t]/) {
$thisline .= $lookahead;
}
else {
last LINE;
}
}
return $thisline;
}
$lookahead = <STDIN>; # get first line
while (defined($line = get_line())) {
...
}
and here's you naming your arguments by assigning to a list of private variables, chef's kiss โจ:
sub maybeset {
my($key, $value) = @_;
$Foo{$key} = $value unless $Foo{$key};
}
because that assignment copies the values, it also has the effect of turning call-by-reference into call-by-value ๐
. otherwise, a function is totally free to do in-place modifications of @_ and change its caller's values. like this:
upcase_in($v1, $v2); # this changes $v1 and $v2
sub upcase_in {
for (@_) { tr/a-z/A-Z/ }
}
you are not allowed to modify constants this way, obviously ๐ซ. if an argument were actually a literal and you tried to change it, you'd take a (presumably fatal) exception. for example, this will not work:
upcase_in("frederick");
it would be so much safer if the upcase_in() function were written to return a copy of its parameters instead of changing them in place ๐ซถ:
($v3, $v4) = upcase($v1, $v2); # this doesn't change $v1 and $v2
sub upcase {
return unless defined wantarray; # void context, do nothing
my @parms = @_;
for (@parms) { tr/a-z/A-Z/ }
return wantarray ? @parms : $parms[0];
}
notice how this (unprototyped) function does not care whether it was handed real scalars or arrays ๐. Perl sees all arguments as one big, long, flat parameter list in @_. this is one area where Perl's simple argument-passing style literally shines โจ. the upcase() function would work perfectly fine without changing the upcase() definition at all, even if we fed it stuff like this:
@newlist = upcase(@list1, @list2);
@newlist = upcase( split /:/, $var );
do NOT, however, be tempted to do this ๐:
(@x, @y) = upcase(@list1, @list2);
just like the incoming parameter list gets flattened, the return list is also flattened on return. so all you've managed to do here is stuff everything into @x and leave @y completely empty ๐. for alternatives, see "Pass by Reference".
a subroutine can be called using an explicit & prefix. the & is optional in modern Perl, and so are parentheses, as long as the subroutine has been predeclared. but โ and this is the important bit โ the & is not optional when you're just naming the subroutine, like when it's used as an argument to defined() or undef(). it's also not optional when you wanna do an indirect subroutine call with a subroutine name or reference using the &$subref() or "&{$subref}()" constructs, although the $subref->() notation solves that whole problem for you ๐. see perlref for more about all of that.
subroutines can be called recursively ๐. if a subroutine is called using the & form, the argument list is optional, and if you omit it, no @_ array gets set up for the subroutine at all โ instead, the @_ array from the time of the call is visible to the subroutine ๐. this is an efficiency mechanism that new users may wish to avoid. ngl, listen to that advice.
&foo(1,2,3); # pass three arguments
foo(1,2,3); # the same
foo(); # pass an empty argument list
&foo(); # the same
&foo; # foo() gets current args, like foo(@_)!
use strict 'subs';
foo; # like foo() iff sub foo predeclared, else
# a compile-time error
no strict 'subs';
foo; # like foo() iff sub foo predeclared, else
# a literal string "foo"
and it's not just that the & form makes the argument list optional โ it also disables any prototype checking on arguments you do provide ๐ฅ. part of that is for historical reasons, and part of it is for having a convenient way to cheat if you know what you're doing ๐. see "Prototypes" below.
since Perl 5.16.0, the __SUB__ token is available under use feature 'current_sub' and "use v5.16". it evaluates to a reference to the currently-running sub, which means you can do recursive calls without even knowing your subroutine's name ๐คฏ:
use v5.16;
my $factorial = sub {
my ($x) = @_;
return 1 if $x == 1;
return($x * __SUB__->( $x - 1 ) );
};
โ ๏ธ heads up bestie: the behavior of__SUB__inside a regex code block (like"/(?{...})/") is subject to change. so like, don't build your whole personality on it.
subroutines whose names are in all upper case are reserved to the Perl core ๐, and so are modules whose names are in all lower case. a subroutine in all capitals is a loosely-held convention meaning it'll be called indirectly by the run-time system itself, usually because some event got triggered. subroutines whose name starts with a left parenthesis are also reserved in the same way. here's a list of some subroutines that currently do special, pre-defined things ๐ฆ:
- documented later in this document
"AUTOLOAD"
- documented in perlmod
"CLONE","CLONE_SKIP"
- documented in perlobj
"DESTROY","DOES"
and bestie we are literally only getting started ๐ญ this is part one and there's so much more โ do not go anywhere ๐
- documented in
perltie"BINMODE","CLEAR","CLOSE","DELETE","DESTROY","EOF","EXISTS","EXTEND","FETCH","FETCHSIZE","FILENO","FIRSTKEY","GETC","NEXTKEY","OPEN","POP","PRINT","PRINTF","PUSH","READ","READLINE","SCALAR","SEEK","SHIFT","SPLICE","STORE","STORESIZE","TELL","TIEARRAY","TIEHANDLE","TIEHASH","TIESCALAR","UNSHIFT","UNTIE","WRITE"
- documented in
PerlIO::via"BINMODE","CLEARERR","CLOSE","EOF","ERROR","FDOPEN","FILENO","FILL","FLUSH","OPEN","POPPED","PUSHED","READ","SEEK","SETLINEBUF","SYSOPEN","TELL","UNREAD","UTF8","WRITE"
- documented in
perlfunc"import","unimport","INC"
- documented in
UNIVERSAL"VERSION"
- documented in
perldebguts"DB::DB","DB::sub","DB::lsub","DB::goto","DB::postponed"
- undocumented, used internally by the overload feature
- any starting with
"("
- any starting with
The "BEGIN", "UNITCHECK", "CHECK", "INIT" and "END" subroutines are lowkey not subroutines at all bestie โ they're named special code blocks, and the gag is you can have more than one of them in a package, and you can not call them explicitly. Ever. ๐ Go peek at "BEGIN, UNITCHECK, CHECK, INIT and END" in perlmod for the full lore.
โจ Signatures โจ ๐ซถ
Okay so slay, Perl has a whole facility that lets you declare a subroutine's formal parameters with special syntax, kept separate from the actual procedural code of the subroutine body. That formal parameter list? That's what we call a signature. ๐
It has to be enabled before you can use it. It gets turned on automatically by a use v5.36 (or anything higher), or more directly, like, just say it out loud with use feature 'signatures', in the current scope.
The signature is part of a subroutine's body, bestie. Normally a subroutine's body is just a braced block of code, but the moment you're using a signature, the signature is a parenthesised list that sits immediately before the block โ after any name or attributes. Like so:
sub foo :lvalue ($x, $y = 1, @z) { .... }
The signature declares lexical variables that are in scope for the block. When the subroutine gets called, the signature takes control first. It populates the signature variables from the list of arguments that were passed. And if the argument list doesn't meet the requirements of the signature? It throws an exception. No negotiation, no vibes, just an exception. Then once signature processing is done, control passes to the block. โจ
Positional parameters get handled by simply naming scalar variables in the signature. Example:
sub foo ($left, $right) {
return $left + $right;
}
That takes two positional parameters, and both of them must be filled at runtime by two arguments. By default, parameters are mandatory, and you are not permitted to pass more arguments than expected. So the above is equivalent to:
sub foo {
die "Too many arguments for subroutine" unless @_ <= 2;
die "Too few arguments for subroutine" unless @_ >= 2;
my $left = $_[0];
my $right = $_[1];
return $left + $right;
}
See? It's giving manual labour. ๐ญ
You can also justโฆ ignore an argument, by omitting the main part of the name from the parameter declaration and leaving behind a bare $ sigil. Like:
sub foo ($first, $, $third) {
return "first=$first, third=$third";
}
And even though that ignored argument never goes into a variable, it's still mandatory for the caller to pass it. The audacity, honestly. ๐
A positional parameter becomes optional when you give it a default value, separated from the parameter name by =:
sub foo ($left, $right = 0) {
return $left + $right;
}
That subroutine can be called with either one or two arguments. And here's the cute part: the default value expression is evaluated when the subroutine is called, so it can totally hand out different default values for different calls. It's only evaluated if the argument was actually omitted from the call. Example:
my $auto_id = 0;
sub foo ($thing, $id = $auto_id++) {
print "$thing has ID $id";
}
Which automatically assigns distinct sequential IDs to things that nobody supplied an ID for. Main character energy, fr fr. ๐
A default value expression can also refer to parameters earlier in the signature, which makes the default for one parameter vary depending on the earlier parameters. Example:
sub foo ($first_name, $surname, $nickname = $first_name) {
print "$first_name $surname is known as \"$nickname\"";
}
Since Perl 5.38, a default value expression can also be written using the //= operator โ it gets evaluated and used if the caller omitted a value, or if the value they provided was undef:
sub foo ($name //= "world") {
print "Hello, $name";
}
foo(undef); # will print "Hello, world"
And similarly since Perl 5.38, the ||= operator can be used to provide a default expression that gets used whenever the caller provided a false value. (And remember bestie: a missing value and an undef value are also false. ๐)
sub foo ($x ||= 10) {
return 5 + $x;
}
An optional parameter can be nameless, exactly like a mandatory parameter. Behold:
sub foo ($thing, $ = 1) {
print $thing;
}
The parameter's default value will still get evaluated if the corresponding argument isn't supplied โ even though the value won't be stored anywhere. That's deliberate, in case evaluating it has important side effects. But! It gets evaluated in void context, so if it doesn't have side effects and isn't trivial, it'll generate a warning when the void warning category is enabled. If a nameless optional parameter's default value isn't important, you can just omit it the same way you omitted the parameter's name:
sub foo ($thing, $=) {
print $thing;
}
Optional positional parameters must come after all mandatory positional parameters. (Unless there are no mandatory positional parameters at all โ then the optional positional parameters can be the very first thing in the signature, go off โจ) If there are multiple optional positional parameters and not enough arguments are supplied to fill them all, they get filled from left to right.
Since Perl 5.43.5, a signature can also declare named parameters. Just like positional parameters, these are lexical variables that will contain values passed by the caller when the subroutine is invoked. The difference: positional parameters take their values from the corresponding position in the list the caller passed, whereas named parameters are matched by name-value pairs from the caller. The passed-in name matches the variable name of the parameter, but the order of the pairs is not significant. ๐
โ ๏ธ Named parameters in signatures are currently considered experimental, and their behaviour may change in future releases of Perl. Uses of named parameters in a signature will currently emit a warning in the experimental::signature_named_parameters category.
Named parameters are declared with a prefixed : symbol in front of the variable sigil and name. That symbol is not part of the variable's name within the body of the subroutine. Named parameters may only be declared after any positional parameters, and further positional parameters are not allowed after any named ones.
sub foo (:$alpha, :$beta) {
print "The value of alpha was $alpha\n";
}
To invoke this function, the caller must pass pairs of names and values to provide values for the parameters. Each name must match the name of one of the variables, omitting its leading $ sigil. The order of these values is not important โ both of these lines cause the exact same behaviour:
foo(alpha => "A", beta => "B");
foo(beta => "B", alpha => "A");
If a function declares both positional and named parameters, then callers must provide values for all positional parameters before providing values for named parameters โ even if the positional parameters have default values. Yeah. Rules are rules. ๐
It doesn't matter where these parameter names come from in the caller. In simple cases they could be literal strings, like in the previous example, or they could themselves come from other variables. Expanding a hash variable into the caller list is a super convenient way to collect multiple variables at once:
my %params = (
alpha => "X",
beta => "Y",
);
foo(%params);
As with positional parameters, named parameters may be declared with a defaulting expression, which provides a value to assign into the variable if the caller doesn't provide one. Any parameters that don't have a defaulting expression become mandatory, and an exception is raised if the caller doesn't provide an associated value.
sub foo (:$x, :$y = 123) { ... }
foo(y => 456); # will complain that 'x' is missing
foo(x => 789); # is allowed, $y will take its default value
Any of the =, //= or ||= operators may be used to provide the defaulting expression, with the same semantics as for positional parameters. ๐
The defaulting expressions for optional named parameters are invoked in order, left to right, as required. And as with positional parameters, each expression can see and make use of the values assigned to any previous parameter. Teamwork, bestie. ๐ซถ
If the subroutine already declares any optional positional parameters, then all named parameters must also be optional. However โ if the subroutine doesn't declare any optional positional parameters, then the named ones may be freely mixed between mandatory and optional, since they're processed by name and not by position. Slay.
After positional or named parameters, additional arguments may be captured in a slurpy parameter. ๐ The simplest form of this is just an array variable:
sub foo ($filter, @inputs) {
print $filter->($_) foreach @inputs;
}
With a slurpy parameter in the signature, there is no upper limit on how many arguments may be passed. A slurpy array parameter may be nameless, just like a positional parameter โ in which case its only effect is to turn off the argument limit that would otherwise apply:
sub foo ($thing, @) {
print $thing;
}
A slurpy parameter may instead be a hash, in which case the arguments available to it are interpreted as alternating keys and values. There must be as many keys as values: if there's an odd argument, then an exception will be thrown. ๐ญ Keys get stringified, and if there are duplicates, the later instance takes precedence over the earlier one โ same as with standard hash construction.
sub foo ($filter, %inputs) {
print $filter->($_, $inputs{$_}) foreach sort keys %inputs;
}
A slurpy hash parameter may be nameless, just like other kinds of parameter. It still insists that the number of arguments available to it be even, even though they're not being put into a variable. Commitment to the bit. ๐
- slurpy parameter ๐ โ OK so a slurpy (that's an array or a hash) has to be the last thing in the signature, periodt. It can come after mandatory + optional positional params and named params, and honestly it can also be the only thing chillin' in the signature. But bestie, slurpy params cannot have default values โ if nobody passes anything for them, you just get an empty array or an empty hash. That's the deal.
- Also! The presence of a slurpy parameter changes how a sub with named parameters behaves when the caller passes a name that doesn't match any named parameter the sub declared. ๐ณ
- Without a slurpy, any extra unrecognised names throw an exception. With a slurpy, those unrecognised names and values get collected there instead. It's giving "catch-all bucket energy" ๐ชฃโจ
sub foo (:$x, @rest) { ... }
foo(x => "one", y => "two"); # @rest will be ("y", "two")
sub foo (:$x, %rest) { ... }
foo(x => "one", y => "two"); # %rest will be (y => "two")
- A signature can also be completely empty, and in that case all it does is check that the caller passed no arguments. Iconic minimalism ๐
sub foo () {
return 123;
}
To summarize, a signature contains, in order:
- zero or more mandatory positional scalar parameters
- zero or more optional positional scalar parameters
- zero or more mandatory or optional named scalar parameters
- zero or one slurpy array or hash parameter
Prior to Perl 5.36 these were considered experimental, and they'd emit a warning in the "experimental::signatures" category. From Perl 5.36 onwards that stops happening โ but heads up, the warning category still exists for back-compatibility with code that tries to disable it like this:
no warnings 'experimental::signatures';
Now, in the current Perl implementation, when you're using a signature the arguments are still also available in the special array variable @_. ๐ BUT โ accessing them via that array is now discouraged, and you should not rely on it in newly-written code, because this ability may change in a future version. And code that tries to touch the @_ array when compiled will produce warnings in the "experimental::args_array_with_signatures" category:
sub f ($x) {
# This line emits the warning seen below
print "Arguments are @_";
}
Use of @_ in join or string with signatured subroutine is
experimental at ...
๐จ There's a real difference between the two ways of grabbing args, bestie:@_aliases the arguments, but the signature variables get copies. So writing to a signature variable only changes that variable โ the caller's variables are untouched. But writing to an element of@_modifies whatever the caller used to supply that argument. No cap, that's a big deal. ๐ญ
There's a potential syntactic ambiguity between signatures and prototypes (peep "Prototypes"), because both of them start with an opening parenthesis, and both can show up in some of the same places โ like right after the name in a subroutine declaration. For historical reasons, when signatures are not enabled, any opening parenthesis in that kind of context triggers some very forgiving prototype parsing. Most signatures will get read as prototypes in those situations โ but they won't be valid prototypes. (A valid prototype cannot contain any alphabetic character.) And that leads to some genuinely confusing error messages. ๐
To dodge the ambiguity, when signatures are enabled the special syntax for prototypes is disabled. Perl makes no attempt to guess whether a parenthesised group was meant to be a prototype or a signature. So to give a subroutine a prototype in those circumstances, you use a prototype attribute. Like:
sub foo :prototype($) { $_[0] }
It's entirely possible for a sub to have both a prototype and a signature โ they just do different jobs:
- the prototype affects compilation of calls to the sub
- the signature puts argument values into lexical variables at runtime
So you can absolutely write:
sub foo :prototype($$) ($left, $right) {
return $left + $right;
}
The prototype attribute โ and any other attributes โ must come before the signature. And the signature always immediately precedes the block of the subroutine's body. Order matters, bestie. ๐
๐ฆ Private Variables via my() ๐ฆ
Synopsis:
my $foo; # declare $foo lexically local
my (@wid, %get); # declare list of variables local
my $foo = "flurp"; # declare $foo lexical, and init it
my @oof = @bar; # declare @oof lexical, and init it
my $x : Foo = $y; # similar, with an attribute applied
โ ๏ธ WARNING: The use of attribute lists on"my"declarations is still evolving. The current semantics and interface are subject to change. SeeattributesandAttribute::Handlers.
The "my" operator declares the listed variables to be lexically confined to the enclosing block, conditional ("if"/"unless"/"elsif"/"else"), loop ("for"/"foreach"/"while"/"until"/"continue"), subroutine, "eval", or "do"/"require"/"use"'d file. If you list more than one value, the list must go in parentheses. All listed elements must be legal lvalues. And only alphanumeric identifiers may be lexically scoped โ magical built-ins like $/ currently have to be "local"ized with "local" instead, if you wanna limit their scope dynamically. That's just how it is. ๐
Unlike global or package variables localized by the "local" operator, lexical variables declared with "my" are totally hidden from the outside world โ including from any called subroutines. And this holds true even when it's the same subroutine calling itself or being called from elsewhere โ every call gets its own copy. ๐ฑ
But wait, this doesn't mean a "my" variable declared in a statically enclosing lexical scope would be invisible. Only dynamic scopes get cut off. For example, the bumpx() function below has access to the lexical $x variable, because both the "my" and the "sub" happened at the same scope โ presumably file scope:
my $x = 10;
sub bumpx { $x++ }
An eval(), however, can see lexical variables of the scope it's being evaluated in โ as long as the names aren't hidden by declarations inside the eval() itself. See perlref. โจ
The parameter list to my() may be assigned to if you want, which lets you initialize your variables. (If no initializer is given for a particular variable, it's created with the undefined value.) Usually this is how you name input parameters to a subroutine. Examples:
$arg = "fred"; # "global" variable
$n = cube_root(27);
print "$arg thinks the root is $n\n";
# outputs: fred thinks the root is 3
sub cube_root {
my $arg = shift; # name doesn't matter
$arg **= 1/3;
return $arg;
}
The "my" is basically just a modifier on something you might assign to. So when you assign to variables in its argument list, "my" doesn't change whether those variables get viewed as a scalar or an array. So:
my ($foo) = <STDIN>; # WRONG?
my @FOO = <STDIN>;
Both of those supply a list context to the right-hand side, while:
my $foo = <STDIN>;
supplies a scalar context. But here's the gotcha โ the following declares only one variable:
my $foo, $bar = 1; # WRONG
Because that has the same effect as:
my $foo;
$bar = 1;
๐ญ yeah. And the declared variable is not introduced (not visible) until after the current statement. So:
my $x = $x;
can be used to initialize a new $x with the value of the old $x. And this expression:
my $x = 123 and $x == 123
is false โ unless the old $x just happened to have the value 123. Sneaky. ๐
Lexical scopes of control structures are not bounded precisely by the braces that delimit their controlled blocks โ the control expressions are part of that scope too. So in this loop:
while (my $line = <>) {
$line = lc $line;
} continue {
print $line;
}
the scope of $line extends from its declaration throughout the rest of the loop construct (including the "continue" clause) โ but not beyond it. Similarly, in the conditional:
if ((my $answer = <STDIN>) =~ /^yes$/i) {
user_agrees();
} elsif ($answer =~ /^no$/i) {
user_disagrees();
} else {
chomp $answer;
die "'$answer' is neither 'yes' nor 'no'";
}
the scope of $answer extends from its declaration through the rest of that conditional, including any "elsif" and "else" clauses โ but not beyond it. See "Simple Statements" in perlsyn for info on the scope of variables in statements with modifiers. ๐
The "foreach" loop defaults to scoping its index variable dynamically, the "local" way. BUT โ if the index variable is prefixed with the keyword "my", or if there's already a lexical by that name in scope, then a new lexical is created instead. So in this loop:
for my $i (1, 2, 3) {
some_function();
}
the scope of $i extends to the end of the loop โ but not beyond it โ which means the value of $i is inaccessible inside some_function(). Wild, right? ๐
Some users like to encourage lexically scoped variables. So as an aid to catching implicit uses of package variables (which are always global), if you say:
use strict 'vars';
then any variable mentioned from there to the end of the enclosing block must either:
- refer to a lexical variable,
- be predeclared via
"our"or"use vars", - or else be fully qualified with the package name.
Otherwise you get a compilation error. An inner block can countermand this with "no strict 'vars'". Periodt. ๐
A "my" has both a compile-time and a run-time effect:
- At compile time, the compiler takes notice of it. Its main usefulness is to quiet
"use strict 'vars'", but it's also essential for generating closures, as detailed inperlref. - Actual initialization is delayed until run time though โ so it gets executed at the appropriate time, like each time through a loop, for example. โฐ
Variables declared with "my" are not part of any package, and therefore are never fully qualified with the package name. In particular, you're not allowed to try to make a package variable (or any other global) lexical:
my $pack::var; # ERROR! Illegal syntax
In fact, a package or global variable is still accessible using the fully qualified "::" notation, even while a lexical of the same name is also visible:
package main;
our $x = 10;
my $x = 20;
print "$x and $::x\n";
And that will print out 20 and 10. Both vibing at once. ๐
okay bestie, real talk โ you can also declare my variables at the absolute outermost scope of a file, and that hides those identifiers from literally everything outside that file. it's giving C's static variables when you use them at file level, no cap. but doing that with a subroutine? that needs a closure (an anonymous function that peeks at the enclosing lexicals ๐ซฃ). so if you want a private sub that nobody outside that block can call, just have it declare a lexical variable holding an anonymous sub reference:
my $secret_version = '1.001-beta';
my $secret_sub = sub { print $secret_version };
$secret_sub->();
as long as that reference never gets returned by any function in the module, no outside module can see the sub โ because its name is not in any package's symbol table. and remember babes, it's not REALLY called $some_pack::secret_version or anything like that. it's just $secret_version, unqualified and unqualifiable ๐
. it has no last name, your honor.
this does not work with object methods though ๐ญ all object methods have to live in some package's symbol table to be findable. see "Function Templates" in perlref for a little work-around.
โจ Persistent Private Variables โจ
there are two ways to build persistent private variables in Perl 5.10, bestie. option one: just use the state feature, simple as. option two: use closures, if you wanna stay compatible with releases older than 5.10 (vintage girlie behavior, respect ๐).
Persistent variables via state()
starting with Perl 5.10.0, you can declare variables with the state keyword instead of my. BUT โ and this is the catch โ you have to have enabled that feature beforehand, either by using the feature pragma, or by using -E on one-liners (see feature). starting with Perl 5.16 though? the CORE::state form does not need the feature pragma. glow up โจ.
so state makes a lexical variable (same scoping rules as my, fr fr) that persists from one subroutine call to the next. and if a state variable lives inside an anonymous subroutine, then each copy of the sub gets its own copy of the state variable. but the value still persists between calls to that same copy of the anonymous subroutine. (do NOT forget that sub { ... } creates a brand new subroutine every single time it runs โ that's the plot twist ๐.)
for example, this code keeps a private counter, incremented every time gimme_another() is called:
use feature 'state';
sub gimme_another { state $x; return ++$x }
and this example uses anonymous subroutines to create separate counters:
use feature 'state';
sub create_counter {
return sub { state $x; return ++$x }
}
also, since $x is lexical, no Perl code outside can reach it or modify it. it's in its own little bubble, protected, iconic ๐.
when combined with variable declaration, a simple assignment to state variables (like state $x = 42) is executed only the first time. when those statements get evaluated on later passes, the assignment is just... ignored. and heads up: the behavior of assignment to state declarations where the left hand side of the assignment involves any parentheses is currently undefined ๐ so don't go there.
Persistent variables with closures
okay so just because a lexical variable is lexically (also called statically) scoped to its enclosing block, eval, or do FILE, that does not mean it works like a C static inside a function. nope. it normally works more like a C auto, but with implicit garbage collection. the duality of perl โจ.
unlike local variables in C or C++, Perl's lexicals don't necessarily get recycled just because their scope has exited. if something more permanent is still aware of the lexical, it sticks around. as long as something else references a lexical, that lexical won't be freed โ which is exactly how it should be, honestly. you wouldn't want memory freed while you're still using it, or kept around after you're done. automatic garbage collection handles all of that for you, no thoughts needed ๐ง.
which means you can pass back or save away references to lexical variables โ whereas returning a pointer to a C auto is a grave error. it also gives us a way to simulate C's function statics. here's the mechanism for giving a function private variables with both lexical scoping and a static lifetime: if you want something like C's static variables, just wrap the whole function in an extra block, and put the static variable outside the function but inside the block.
{
my $secret_val = 0;
sub gimme_another {
return ++$secret_val;
}
}
# $secret_val now becomes unreachable by the outside
# world, but retains its value between calls to gimme_another
if this function is sourced in from a separate file via require or use, then it's probably all good, no notes. but if it's all in the main program, you'll need to arrange for the my to be executed early โ either by putting the whole block above your main program, or, more likely, wrapping just a BEGIN code block around it so it definitely runs before your program starts:
BEGIN {
my $secret_val = 0;
sub gimme_another {
return ++$secret_val;
}
}
see "BEGIN, UNITCHECK, CHECK, INIT and END" in perlmod about the special triggered code blocks โ BEGIN, UNITCHECK, CHECK, INIT and END ๐.
and if declared at the outermost scope (the file scope), then lexicals work kinda like C's file statics. they're available to all functions in that same file declared below them, but inaccessible from outside that file. this strategy is sometimes used in modules to create private variables the whole module can see. lowkey elegant ๐.
๐
Temporary Values via local() ๐
WARNING: in general, you should be usingmyinstead oflocal, because it's faster and safer. periodt.
exceptions to that rule include the global punctuation variables, global filehandles and formats, and direct manipulation of the Perl symbol table itself. local is mostly used when the current value of a variable must be visible to called subroutines. that's its whole moment ๐ซถ.
synopsis, bestie:
# localization of values
local $foo; # make $foo dynamically local
local (@wid, %get); # make list of variables local
local $foo = "flurp"; # make $foo dynamic, and init it
local @oof = @bar; # make @oof dynamic, and init it
local $hash{key} = "val"; # sets a local value for this hash entry
delete local $hash{key}; # delete this entry for the current block
local ($cond ? $v1 : $v2); # several types of lvalues support
# localization
# localization of symbols
local *FH; # localize $FH, @FH, %FH, &FH ...
local *merlyn = *randal; # now $merlyn is really $randal, plus
# @merlyn is really @randal, etc
local *merlyn = 'randal'; # SAME THING: promote 'randal' to *randal
local *merlyn = \$randal; # just alias $merlyn, not @merlyn etc
a local modifies its listed variables to be "local" to the enclosing block, eval, or do FILE โ and to any subroutine called from within that block. so local just gives temporary values to global (meaning package) variables. it does not create a local variable. this is known as dynamic scoping. lexical scoping is done with my, which works more like C's auto declarations. two completely different girlies, don't mix them up ๐ธ.
some types of lvalues can be localized too: hash and array elements and slices, conditionals (provided their result is always localizable), and symbolic references. and as for simple variables, this creates new, dynamically scoped values โจ.
if more than one variable or expression is given to local, they must be placed in parentheses. this operator works by saving the current values of those variables in its argument list on a hidden stack and restoring them upon exiting the block, subroutine, or eval. so called subroutines can also reference the local variable, but not the global one ๐. the argument list may be assigned to if desired, which lets you initialize your local variables. (if no initializer is given for a particular variable, it gets created with an undefined value.)
and because local is a run-time operator, it gets executed every single time through a loop. consequently, it's more efficient to localize your variables outside the loop. efficiency queen behavior ๐
.
Grammatical note on local()
a local is simply a modifier on an lvalue expression. when you assign to a localized variable, the local doesn't change whether its list is viewed as a scalar or an array. so:
local($foo) = <STDIN>;
local @FOO = <STDIN>;
both of those supply a list context to the right-hand side, while:
local $foo = <STDIN>;
supplies a scalar context. context is everything bestie, don't forget it ๐ฅ.
Localization of special variables
if you localize a special variable, you'll be giving it a new value โ but its magic won't go away. that means all the side-effects related to that magic still work with the localized value โจ.
this feature lets code like this work:
# Read the whole contents of FILE in $slurp
{ local $/ = undef; $slurp = <FILE>; }
note, however, that this restricts localization of some values ๐ญ for example, as of Perl 5.10.0 the following statement dies with an error, Modification of a read-only value attempted, because the $1 variable is magical and read-only:
local $1 = 2;
one exception is the default scalar variable: starting with Perl 5.14, local($_) will always strip all magic from $_, to make it possible to safely reuse $_ in a subroutine. iconic, honestly ๐.
WARNING: localization of tied arrays and hashes does not currently work as described. this will be fixed in a future release of Perl; in the meantime, avoid code that relies on any particular behavior of localising tied arrays or hashes (localising individual elements is still okay). see "Localising Tied Arrays and Hashes Is Broken" in perl58delta for more details.
Localization of globs
the construct:
local *name;
creates a whole new symbol table entry for the glob name in the current package. that means all the variables in its glob slot โ $name, @name, %name, &name, and the name filehandle โ are dynamically reset. all of them, at once, slay ๐.
this implies, among other things, that any magic eventually carried by those variables is locally lost. in other words, saying local */ will not have any effect on the internal value of the input record separator. nope. zero effect. it's giving nothing ๐.
Localization of elements of composite types
Okay so real quick โ what even happens when you localize a member of a composite type? Like an array element or a hash element? Bestie, it gets localized by name. Meaning: when the scope of the local() ends, the saved value gets restored to the hash element whose key was named in the local(), or the array element whose index was named in the local().
And if that element got deleted while the local() was active โ say someone did a delete() on a hash or a shift() on an array ๐ญ โ it will spring back into existence, possibly stretching out an array and filling the skipped slots with undef. Like a glow-up resurrection moment fr. For instance, if you say:
%hash = ( 'This' => 'is', 'a' => 'test' );
@ary = ( 0..5 );
{
local($ary[5]) = 6;
local($hash{'a'}) = 'drill';
while (my $e = pop(@ary)) {
print "$e . . .\n";
last unless $e > 3;
}
if (@ary) {
$hash{'only a'} = 'test';
delete $hash{'a'};
}
}
print join(' ', map { "$_ $hash{$_}" } sort keys %hash),".\n";
print "The array has ",scalar(@ary)," elements: ",
join(', ', map { defined $_ ? $_ : 'undef' } @ary),"\n";
Perl will print ๐
6 . . .
4 . . .
3 . . .
This is a test only a test.
The array has 6 elements: 0, 1, 2, undef, undef, 5
Real talk though: the behavior oflocal()on non-existent members of composite types is subject to change in future. And the behavior oflocal()on array elements specified using negative indexes? Particularly surprising, and very likely to change. Like, do not build your whole personality on that, bestie.
โจ Localized deletion of elements of composite types โจ
Okay this one is chef's kiss. You can use the delete local $array[$idx] and delete local $hash{key} constructs to delete a composite type entry for the current block and then restore it when the block ends ๐ซถ.
They return the array/hash value from before the localization, which means they're respectively equivalent to:
do {
my $val = $array[$idx];
local $array[$idx];
delete $array[$idx];
$val
}
and
do {
my $val = $hash{key};
local $hash{key};
delete $hash{key};
$val
}
...except that for those, the local is scoped to the do block. Slices are also accepted, no cap:
my %hash = (
a => [ 7, 8, 9 ],
b => 1,
)
{
my $x = delete local $hash{a};
# $x is [ 7, 8, 9 ]
# %hash is (b => 1)
{
my @nums = delete local @$x[0, 2]
# @nums is (7, 9)
# $x is [ undef, 8 ]
$x[0] = 999; # will be erased when the scope ends
}
# $x is back to [ 7, 8, 9 ]
}
# %hash is back to its original state
This construct is supported since Perl v5.12 ๐.
๐ธ Lvalue subroutines ๐ธ
So you can return a modifiable value from a subroutine. Iconic. To do that, you have to declare the subroutine to return an lvalue:
my $val;
sub canmod : lvalue {
$val; # or: return $val;
}
sub nomod {
$val;
}
canmod() = 5; # assigns to $val
nomod() = 5; # ERROR
The scalar/list context for the subroutine and for the right-hand side of the assignment is determined as if the subroutine call is replaced by a scalar. For example, consider:
data(2,3) = get_data(3,4);
Both subroutines here get called in a scalar context, while in:
(data(2,3)) = get_data(3,4);
and in:
(data(2),data(3)) = get_data(3,4);
all the subroutines get called in a list context. Slay.
Lvalue subroutines are convenient and all, but bestie you have to keep in mind that when you use them with objects, they may violate encapsulation ๐. A normal mutator can check the supplied argument before setting the attribute it's protecting โ an lvalue subroutine cannot. If you require any special processing when storing and retrieving the values, consider using the CPAN module Sentinel or something similar.
๐ฆ Lexical Subroutines ๐ฆ
Beginning with Perl 5.18, you can declare a private subroutine with my or state. Just like with state variables, the state keyword is only available under use feature 'state' or use v5.10 or higher.
Prior to Perl 5.26, lexical subroutines were deemed experimental (๐จ) and were available only under the use feature 'lexical_subs' pragma. They also produced a warning unless the experimental::lexical_subs warnings category was disabled.
These subroutines are only visible within the block in which they are declared, and only after that declaration:
# Include these two lines if your code is intended to run under Perl
# versions earlier than 5.26.
no warnings "experimental::lexical_subs";
use feature 'lexical_subs';
foo(); # calls the package/global subroutine
state sub foo {
foo(); # also calls the package subroutine
}
foo(); # calls "state" sub
my $ref = \&foo; # take a reference to "state" sub
my sub bar { ... }
bar(); # calls "my" sub
And no, you can't (directly) write a recursive lexical subroutine ๐:
# WRONG
my sub baz {
baz();
}
This example fails because baz() refers to the package/global subroutine baz, not the lexical subroutine currently being defined. The solution is to use __SUB__:
my sub baz {
__SUB__->(); # calls itself
}
You can predeclare a lexical subroutine. The sub foo {...} subroutine definition syntax respects any previous my sub; or state sub; declaration. But using this to define recursive subroutines is a bad idea, however:
my sub baz; # predeclaration
sub baz { # define the "my" sub
baz(); # WRONG: calls itself, but leaks memory
}
Just like my $f; $f = sub { $f->() }, this example leaks memory ๐. The name baz is a reference to the subroutine, and the subroutine uses the name baz โ they keep each other alive (see "Circular References" in perlref). Codependent in the worst way tbh.
๐ state sub vs my sub ๐
What's the difference between state subs and my subs? Each time execution enters a block where my subs are declared, a new copy of each sub is created. state subroutines persist from one execution of the containing block to the next.
So, in general, state subroutines are faster . But my subs are necessary if you want to create closures:
sub whatever {
my $x = shift;
my sub inner {
... do something with $x ...
}
inner();
}
In this example, a new $x is created when whatever is called, and also a new inner, which can see the new $x. A state sub will only see the $x from the first call to whatever. Like it's stuck in the past fr fr.
๐ our subroutines ๐
Like our $variable, our sub creates a lexical alias to the package subroutine of the same name.
The two main uses for this are to switch back to using the package sub inside an inner scope:
sub foo { ... }
sub bar {
my sub foo { ... }
{
# need to use the outer foo here
our sub foo;
foo();
}
}
and to make a subroutine visible to other packages in the same scope:
package MySneakyModule;
our sub do_something { ... }
sub do_something_with_caller {
package DB;
() = caller 1; # sets @DB::args
do_something(@args); # uses MySneakyModule::do_something
}
๐ Passing Symbol Table Entries (typeglobs) ๐
WARNING: The mechanism described in this section was originally the only way to simulate pass-by-reference in older versions of Perl. While it still works fine in modern versions, the new reference mechanism is generally easier to work with. See below.
Sometimes you don't want to pass the value of an array to a subroutine โ you want to pass the name of it, so the subroutine can modify the global copy instead of working with a local copy. In Perl you can refer to all objects of a particular name by prefixing the name with a star: *foo. This is often known as a "typeglob", because the star on the front can be thought of as a wildcard match for all the funny prefix characters on variables and subroutines and such. Cute little wildcard energy โญ.
When evaluated, the typeglob produces a scalar value that represents all the objects of that name, including any filehandle, format, or subroutine. When assigned to, it causes the name mentioned to refer to whatever * value was assigned to it. Example:
sub doubleary {
local(*someary) = @_;
foreach $elem (@someary) {
$elem *= 2;
}
}
doubleary(*foo);
doubleary(*bar);
Scalars are already passed by reference, so you can modify scalar arguments without using this mechanism by referring explicitly to $_[0] etc. You can modify all the elements of an array by passing all the elements as scalars, but you have to use the * mechanism (or the equivalent reference mechanism) to push, pop, or change the size of an array. It will certainly be faster to pass the typeglob (or reference).
Even if you don't want to modify an array, this mechanism is useful for passing multiple arrays in a single LIST, because normally the LIST mechanism will merge all the array values so that you can't extract out the individual arrays ๐ญ. For more on typeglobs, see "Typeglobs and Filehandles" in perldata.
๐ When to Still Use local() ๐
Despite the existence of my, there are still three places where the local operator still shines โจ. In fact, in these three places, you must use local instead of my.
- You need to give a global variable a temporary value, especially
$_.
The global variables, like @ARGV or the punctuation variables, must be localized with local(). This block reads in /etc/motd, and splits it up into chunks separated by lines of equal signs, which are placed in @Fields:
{
local @ARGV = ("/etc/motd");
local $/ = undef;
local $_ = <>;
@Fields = split /^\s*=+\s*$/;
}
In particular, it's important to localize $_ in any routine that assigns to it. Look out for implicit assignments in while conditionals ๐.
- You need to create a local file or directory handle or a local function.
A function that needs its own filehandle โ like, its very own baby handle, not one it's borrowing from the group chat โ has to call local() on a complete typeglob. And that's not a bug bestie that's a feature, because it means you can literally conjure brand new symbol table entries out of thin air:
sub ioqueue {
local (*READER, *WRITER); # not my!
pipe (READER, WRITER) or die "pipe: $!";
return (*READER, *WRITER);
}
($head, $tail) = ioqueue();
See that lil # not my! comment? ๐ธ Because my is not the move here, okurrr โ local on the whole typeglob is. And if you wanna make anonymous symbol table entries instead, go peep the Symbol module. ๐ฆ
So here's the tea: assigning a reference to a typeglob creates an alias. Which is why you can use this to build what is effectively a local function โ or at the very least, a local alias:
{
local *grow = \&shrink; # only until this block exits
grow(); # really calls shrink()
move(); # if move() grow()s, it shrink()s too
}
grow(); # get the real grow() again
Look at those comments, they are serving so much truth ๐
. Inside the block, grow() is literally shrink(). And even move() gets swept up in it if it happens to call grow() internally. Then the second you leave the block? Girl, grow() is back to being the real grow(). Identity crisis fully resolved. โจ
For more on manipulating functions by name in this way, see "Function Templates" in perlref.
3. You want to temporarily change just one element of an array or hash ๐
Ok so this one is actually so cute. You can local-ize just one single element of an aggregate. Usually this is done on dynamics (the symbol-table ones):
{
local $SIG{INT} = 'IGNORE';
funct(); # uninterruptible
}
# interruptibility automatically restored here
So funct() runs and it's just... uninterruptible. Nothing is getting through to it. But the moment that block exits, your interruptibility is automatically restored โ no manual cleanup, no leftover mess, she literally heals herself. ๐
And ngl, it works on lexically declared aggregates too, so don't go thinking this is a dynamics-only situation. ๐
Pass by Reference ๐ฆ
Ok bestie, this is the part where people start fighting in the comments. If you wanna pass more than one array or hash into a function โ or return more than one out of it โ and have them keep their integrity (i.e. not melt into one giant soup), then you're gonna have to use an explicit pass-by-reference. There is no shortcut, no cap. ๐ซถ
But before you do any of that, you need to actually understand references, and that's all detailed in perlref. Without that, this section may not make much sense to you, and that's genuinely fine. ๐
Here's a few simple examples. First up: pass in several arrays to a function and have it pop all of them, returning a fresh new list of all their former last elements:
@tailings = popmany ( \@w, \@x, \@y, \@z );
sub popmany {
my $aref;
my @retlist;
foreach $aref ( @_ ) {
push @retlist, pop @$aref;
}
return @retlist;
}
And here's how you might write a function that returns a list of keys occurring in all the hashes passed to it:
@common = inter( \%foo, \%bar, \%joe );
sub inter {
my ($k, $href, %seen); # locals
foreach $href (@_) {
while ( $k = each %$href ) {
$seen{$k}++;
}
}
return grep { $seen{$_} == @_ } keys %seen;
}
See how $seen{$k}++ counts up every key, and then grep { $seen{$_} == @_ } only keeps the ones that showed up in every single hash? Intersection. Slay. ๐
So far we've been using just the normal list return mechanism. But what if you wanna pass or return a hash? Well โ if you're only using one of them, or you honestly don't mind them concatenating together, then the normal calling convention is ok. Although it's a lil expensive. ๐ธ
Where people get into trouble is right here:
(@w, @x) = func(@y, @z);
or
(%w, %x) = func(%y, %z);
That syntax simply will not work. It sets just @w or %w and then it clears the @x or %x โ gone, poof, bye. And on top of that tragedy, the function never even got two separate arrays or hashes anyway: it got one long list in @_, as always. ๐ฅฒ
If you can get everyone on board with dealing through references, the code ends up cleaner โ although ngl, not so nice to look at. Here's a function that takes two array references as arguments and returns the two array elements in order of how many elements they have in them:
($wref, $xref) = func(\@y, \@z);
print "@$wref has more than @$xref\n";
sub func {
my ($yref, $zref) = @_;
if (@$yref > @$zref) {
return ($yref, $zref);
} else {
return ($zref, $yref);
}
}
And it turns out you can actually do this too:
(*w, *x) = func(\@y, \@z);
print "@w has more than @x\n";
sub func {
local (*y, *z) = @_;
if (@y > @z) {
return (\@y, \@z);
} else {
return (\@z, \@y);
}
}
Here we're using the typeglobs to do that symbol table aliasing thing. It's a tad subtle though โ and it also won't work if you're using my variables, because only globals (even ones in disguise as locals) are actually in the symbol table. ๐ซ
If you're passing around filehandles, you could usually just use the bare typeglob, like *STDOUT โ but typeglob references work too. For example:
splutter(\*STDOUT);
sub splutter {
my $fh = shift;
print $fh "her um well a hmmm\n";
}
$rec = get_rec(\*STDIN);
sub get_rec {
my $fh = shift;
return scalar <$fh>;
}
And if you're planning on generating new filehandles, you could do this. Notice: you pass back just the bare *FH, not its reference. That distinction matters!! ๐
sub openit {
my $path = shift;
local *FH;
return open (FH, $path) ? *FH : undef;
}
Prototypes ๐
Perl supports a very limited kind of compile-time argument checking using function prototyping. And it can be declared either in the PROTO section or with a prototype attribute. So if you declare either one of these:
sub mypush (\@@)
sub mypush :prototype(\@@)
then mypush() takes arguments exactly like push() does. Periodt. โจ
BUT โ if subroutine signatures are enabled (see "Signatures"), then the shorter PROTO syntax is unavailable, because it would clash with signatures. In that case, a prototype can only be declared in the form of an attribute. No shortcut for you, bestie. ๐ซถ
The function declaration must be visible at compile time. And the prototype affects only the interpretation of regular calls to the function โ where "regular" is defined as not using the & sigil. In other words: if you call it like a built-in function, it behaves like a built-in function. If you call it like an old-fashioned (perl4) subroutine, then it behaves like an old-fashioned subroutine. It naturally falls out from this rule that prototypes have no influence on subroutine references like \&foo or on indirect subroutine calls like &{$subref}() or $subref->(). ๐
Method calls are not influenced by prototypes either, because the function to be called is indeterminate at compile time โ the exact code that gets called depends on inheritance. So prototypes can't peek at that. ๐ฆ
Because the whole intent of this feature is primarily to let you define subroutines that work like built-in functions, here are prototypes for some other functions that parse almost exactly like the corresponding built-in:
Declared as Called as
sub mylink ($$) mylink $old, $new
sub myvec ($$$) myvec $var, $offset, 1
sub myindex ($$;$) myindex getstring(), "substr"
sub mysyswrite ($$$;$) mysyswrite $buf, 0, length($buf) - $off, $off
sub myreverse (@) myreverse $x, $y, $z
sub myjoin ($@) myjoin ":", $x, $y, $z
sub mypop (\@) mypop @array
sub mysplice (\@$$@) mysplice @array, 0, 2, @pushme
sub mykeys (\[%@]) mykeys $hashref->%*
sub myopen (*;$) myopen HANDLE, $name
sub mypipe (**) mypipe READHANDLE, WRITEHANDLE
sub mygrep (&@) mygrep { /foo/ } $x, $y, $z
sub myrand (;$) myrand 42
sub mytime () mytime
Okay so, the backslashed prototype characters: any backslashed prototype character represents an actual argument really using that character for its type. With one exception โ $, which will accept any scalar lvalue expression, such as $foo = 7 or my_function()->[0]. And "using that character for type" means the expression begins with the sigil (optionally preceded by a declarator like my) or ends with the sigil's postfix dereference form. Any of these, for example, satisfies \%:
%hash
%$hashref
my %hash
$hashref->%*
%{ expr }
(expr)->%*
The value passed as part of @_ will be a reference to the actual argument given in the subroutine call โ obtained by applying \ to that argument. ๐ฅ
You can use the \[] backslash group notation to specify more than one allowed argument type. For example:
sub myref (\[$@%&*])
will allow calling myref() as
myref $var
myref @array
myref %hash
myref &sub
myref *glob
and the first argument of myref() will be a reference to a scalar, an array, a hash, a subroutine, or a glob. Pick your fighter. ๐
Unbackslashed prototype characters have special meanings, and here's the cheat sheet:
- Any unbackslashed
@or%eats all remaining arguments, and forces list context. ๐ - An argument represented by
$forces scalar context. - An
&requires an anonymous subroutine, which โ if passed as the first argument โ may look like a bare block: it does not require thesubkeyword or a subsequent comma. - A
*allows the subroutine to accept a bareword, constant, scalar expression, typeglob, or a reference to a typeglob in that slot. The value will be available to the subroutine either as a simple scalar, or (in the latter two cases) as a reference to the typeglob.
And if you wish to always convert such arguments to a typeglob reference, use Symbol::qualify_to_ref() like so:
use Symbol 'qualify_to_ref';
sub foo (*) {
my $fh = qualify_to_ref(shift, caller);
...
}
The + prototype is a special alternative to $ that will act like \[@%] when given a literal array or hash variable, but will otherwise force scalar context on the argument. This is useful for functions which should accept either a literal array or an array reference as the argument:
sub mypush (+@) {
my $aref = shift;
die "Not an array or arrayref" unless ref $aref eq 'ARRAY';
push @$aref, @_;
}
But when you use the + prototype, your function must check that the argument is of an acceptable type. That part is on you. ๐ซ
A semicolon (;) separates mandatory arguments from optional arguments. It's redundant before @ or %, which gobble up everything else anyway. ๐
As the last character of a prototype โ or just before a semicolon, a @ or a % โ you can use _ in place of $: if this argument is not provided, $_ will be used instead. ๐
Now, notice how the last three examples in the table above get treated extra specially by the parser. mygrep() is parsed as a true list operator, myrand() is parsed as a true unary operator with unary precedence exactly the same as rand(), and mytime() is truly without arguments, just like time(). So if you say:
mytime +2;
you'll get mytime() + 2, not mytime(2) โ which is exactly how it would be parsed without a prototype. And if you want to force a unary function to have the same precedence as a list operator, add ; to the end of the prototype:
sub mygetprotobynumber($;);
mygetprotobynumber $x > $y; # parsed as mygetprotobynumber($x > $y)
But okay the actual iconic thing about & is that you can straight-up invent new syntax with it โ as long as it sits in the initial position. Like, you're not just calling a function, you're building a language feature. Slay.
sub try (&@) {
my($try,$catch) = @_;
eval { &$try };
if ($@) {
local $_ = $@;
&$catch;
}
}
sub catch (&) { $_[0] }
try {
die "phooey";
} catch {
/phooey/ and print "unphooey\n";
};
That prints unphooey. Bestie, we just gave Perl a try/catch. ๐
(Yes, there are still unresolved issues having to do with visibility of@_. I'm ignoring that question for the moment. (But note that if we make@_lexically scoped, those anonymous subroutines can act like closures... (Gee, is this sounding a little Lispish? (Never mind.))))
And here's the whole Perl grep operator, just, reimplemented from scratch like it's nothing:
sub mygrep (&@) {
my $code = shift;
my @result;
foreach $_ (@_) {
push(@result, $_) if &$code;
}
@result;
}
Some folks would prefer full alphanumeric prototypes. And those alphanumerics have been intentionally left out of prototypes for the express purpose of someday in the future adding named, formal parameters. The current mechanism's main goal is to let module writers provide better diagnostics for module users. Larry feels the notation is quite understandable to Perl programmers, and that it will not intrude greatly upon the meat of the module, nor make it harder to read. The line noise is visually encapsulated into a small pill that's easy to swallow. ๐
If you try to use an alphanumeric sequence in a prototype you will generate an optional warning โ Illegal character in prototype.... Unfortunately earlier versions of Perl allowed the prototype to be used as long as its prefix was a valid prototype. So the warning may be upgraded to a fatal error in a future version of Perl once the majority of offending code is fixed. Noted. ๐
It's probably best to prototype new functions, not retrofit prototyping into older ones. That's because you must be especially careful about silent impositions of differing list versus scalar contexts. Like, say you decide a function should take just one parameter, like this:
sub func ($) {
my $n = shift;
print "you gave me $n\n";
}
and someone has been calling it with an array or expression returning a list:
func(@foo);
func( $text =~ /\w+/g );
Then you've just supplied an automatic scalar in front of their argument, which can be more than a bit surprising. ๐ญ The old @foo which used to hold one thing doesn't get passed in. Instead, func() now gets passed in a 1; that is, the number of elements in @foo. And the m//g gets called in scalar context so instead of a list of words it returns a boolean result and advances pos($text). Ouch!
If a sub has both a PROTO and a BLOCK, the prototype is not applied until after the BLOCK is completely defined. Which means that a recursive function with a prototype has to be predeclared for the prototype to take effect, like so:
sub foo($$);
sub foo($$) {
foo 1, 2;
}
This is all very powerful, of course, and should be used only in moderation to make the world a better place. ๐
๐งฎ Constant Functions ๐งฎ
Functions with a prototype of () are potential candidates for inlining. If the result after optimization and constant folding is either a constant or a lexically-scoped scalar which has no other references, then it will be used in place of function calls made without &. Calls made using & are never inlined. (See constant for an easy way to declare most constants.)
The following functions would all be inlined:
sub pi () { 3.14159 } # Not exact, but close.
sub PI () { 4 * atan2 1, 1 } # As good as it gets,
# and it's inlined, too!
sub ST_DEV () { 0 }
sub ST_INO () { 1 }
sub FLAG_FOO () { 1 << 8 }
sub FLAG_BAR () { 1 << 9 }
sub FLAG_MASK () { FLAG_FOO | FLAG_BAR }
sub OPT_BAZ () { not (0x1B58 & FLAG_MASK) }
sub N () { int(OPT_BAZ) / 3 }
sub FOO_SET () { 1 if FLAG_MASK & FLAG_FOO }
sub FOO_SET2 () { if (FLAG_MASK & FLAG_FOO) { 1 } }
(Heads up that the last example was not always inlined in Perl 5.20 and earlier, which did not behave consistently with subroutines containing inner scopes.) You can countermand inlining by using an explicit return:
sub baz_val () {
if (OPT_BAZ) {
return 23;
}
else {
return 42;
}
}
sub bonk_val () { return 12345 }
As alluded to earlier you can also declare inlined subs dynamically at BEGIN time if their body consists of a lexically-scoped scalar which has no other references. Only the first example here will be inlined:
BEGIN {
my $var = 1;
no strict 'refs';
*INLINED = sub () { $var };
}
BEGIN {
my $var = 1;
my $ref = \$var;
no strict 'refs';
*NOT_INLINED = sub () { $var };
}
A not so obvious caveat with this (see [RT #79908]) is what happens if the variable is potentially modifiable. For example:
BEGIN {
my $x = 10;
*FOO = sub () { $x };
$x++;
}
print FOO(); # printed 10 prior to 5.32.0
From Perl 5.22 onwards this gave a deprecation warning, and from Perl 5.32 onwards it became a run-time error. ๐จ Previously the variable was immediately inlined, and stopped behaving like a normal lexical variable; so it printed 10, not 11.
If you still want such a subroutine to be inlined (with no warning), make sure the variable is not used in a context where it could be modified aside from where it is declared.
# Fine, no warning
BEGIN {
my $x = 54321;
*INLINED = sub () { $x };
}
# Error
BEGIN {
my $x;
$x = 54321;
*ALSO_INLINED = sub () { $x };
}
Perl 5.22 also introduced the const attribute as an alternative. It was initially experimental, but made stable in Perl 5.40. When applied to an anonymous subroutine, it forces the sub to be called when the sub expression is evaluated. The return value is captured and turned into a constant subroutine:
my $x = 54321;
*INLINED = sub : const { $x };
$x++;
The return value of INLINED in this example will always be 54321, regardless of later modifications to $x. You can also put any arbitrary code inside the sub, and it will be executed immediately and its return value captured the same way. ๐
If you really want a subroutine with a () prototype that returns a lexical variable you can easily force it to not be inlined by adding an explicit return:
BEGIN {
my $x = 10;
*FOO = sub () { return $x };
$x++;
}
print FOO(); # prints 11
The easiest way to tell if a subroutine was inlined is by using B::Deparse. Consider this example of two subroutines returning 1, one with a () prototype causing it to be inlined, and one without (with deparse output truncated for clarity):
$ perl -MO=Deparse -e 'sub ONE { 1 } if (ONE) { print ONE if ONE }'
sub ONE {
1;
}
if (ONE ) {
print ONE() if ONE ;
}
$ perl -MO=Deparse -e 'sub ONE () { 1 } if (ONE) { print ONE if ONE }'
sub ONE () { 1 }
do {
print 1
};
If you redefine a subroutine that was eligible for inlining, you'll get a warning by default. You can use this warning to tell whether or not a particular subroutine is considered inlinable, since it's different than the warning for overriding non-inlined subroutines:
$ perl -e 'sub one () {1} sub one () {2}'
Constant subroutine one redefined at -e line 1.
$ perl -we 'sub one {1} sub one {2}'
Subroutine one redefined at -e line 1.
The warning is considered severe enough not to be affected by the -w switch (or its absence) because previously compiled invocations of the function will still be using the old value of the function. If you need to be able to redefine the subroutine, you need to ensure that it isn't inlined, either by dropping the () prototype (which changes calling semantics, so beware) or by thwarting the inlining mechanism in some other way, e.g. by adding an explicit return, as mentioned above:
sub not_inlined () { return 23 }
๐ญ Overriding Built-in Functions ๐ญ
Many built-in functions may be overridden, though this should be tried only occasionally and for good reason. Typically this might be done by a package attempting to emulate missing built-in functionality on a non-Unix system.
Overriding may be done only by importing the name from a module at compile time โ ordinary predeclaration isn't good enough. However, the use subs pragma lets you, in effect, predeclare subs via the import syntax, and these names may then override built-in ones:
use subs 'chdir', 'chroot', 'chmod', 'chown';
chdir $somewhere;
sub chdir { ... }
To unambiguously refer to the built-in form, precede the built-in name with the special package qualifier CORE::. For example, saying CORE::open() always refers to the built-in open(), even if the current package has imported some other subroutine called &open() from elsewhere. Even though it looks like a regular function call, it isn't: the CORE:: prefix in that case is part of Perl's syntax, and works for any keyword, regardless of what is in the CORE package. Taking a reference to it, that is, \&CORE::open, only works for some keywords. See CORE.
Library modules should not in general export built-in names like open or chdir as part of their default @EXPORT list, because these may sneak into someone else's namespace and change the semantics unexpectedly. ๐ Instead, if the module adds that name to @EXPORT_OK, then it's possible for a user to import the name explicitly, but not implicitly. That is, they could say
use Module 'open';
and it would import the open override. But if they said
use Module;
they would get the default imports without overrides.
okay so the "override built-ins" thing we just did? That one is deliberately locked to the package that asked for the import. Rude little gatekeeper. But there's a second method, and it hits different when you wanna override a built-in everywhere, no namespace boundaries, no permission slips. You do it by importing a sub into the special namespace CORE::GLOBAL::. ๐
Here's an example that <em>quite brazenly</em> replaces the glob operator with something that vibes with regular expressions:
package REGlob;
require Exporter;
@ISA = 'Exporter';
@EXPORT_OK = 'glob';
sub import {
my $pkg = shift;
return unless @_;
my $sym = shift;
my $where = ($sym =~ s/^GLOBAL_// ? 'CORE::GLOBAL' : caller(0));
$pkg->export($where, $sym, @_);
}
sub glob {
my $pat = shift;
my @got;
if (opendir my $d, '.') {
@got = grep /$pat/, readdir $d;
closedir $d;
}
return @got;
}
1;
And bestie, here's how it could be (ab)used:
#use REGlob 'GLOBAL_glob'; # override glob() in ALL namespaces
package Foo;
use REGlob 'glob'; # override glob() in Foo:: only
print for <^[a-z_]+\.pm\$>; # show all pragmatic modules
The first commented-out line is showing off a contrived, even dangerous example. Overriding glob globally means you're forcing that new (and lowkey subversive) behavior on the glob operator for every namespace, with absolutely zero cognizance or cooperation from the modules that own those namespaces. Not the vibe. ๐ฉ
Do this with extreme caution โ if it must be done at all.
Also, that REGlob example does not implement all the support you'd need to cleanly override Perl's glob operator. The built-in glob behaves differently depending on whether it's sitting in a scalar or list context, and our REGlob does not. And honestly? Loads of Perl built-ins have these context-sensitive behaviors, and a properly written override has to support them adequately. Wanna see a fully functional example of overriding glob? Go study the implementation of File::DosGlob in the standard library. ๐
When you override a built-in, your replacement should be consistent (if possible) with the built-in native syntax. You can achieve that with a suitable prototype. To get the prototype of an overridable built-in, call the prototype function with an argument of CORE::builtin_name (see prototype in perlfunc). โจ
But heads up: some built-ins simply can't have their syntax expressed by a prototype โ system and chomp are the examples here. Override those and you won't be able to fully mimic their original syntax. Sorry bestie. ๐ญ
The built-ins do, require and glob can also be overridden, but due to special magic their original syntax is preserved, and you don't have to define a prototype for their replacements. (You can't override the do BLOCK syntax, though.)
require has special additional dark magic: if you invoke your require replacement as require Foo::Bar, it will actually receive the argument Foo/Bar.pm in @_. See require in perlfunc.
And like you noticed from the previous example: if you override glob, the <*> glob operator gets overridden too. Slay, cascading consequences. ๐ฆ
In a similar fashion, overriding the readline function also overrides the equivalent I/O operator <FILEHANDLE>. Also, overriding readpipe also overrides the operators `` and qx//.
Finally: some built-ins (e.g. exists or grep) can't be overridden. Periodt. ๐
๐ซถ Autoloading ๐ซถ
So if you call a subroutine that's undefined, you'd ordinarily get an immediate, fatal error complaining the subroutine doesn't exist. Same deal for subroutines being used as methods, when the method doesn't exist in any base class of the class's package. HOWEVER โ if an AUTOLOAD subroutine is defined in the package or packages used to locate the original subroutine, then that AUTOLOAD subroutine is called with the arguments that would have been passed to the original sub. โจ
The fully qualified name of the original subroutine magically appears in the global $AUTOLOAD variable of the same package as the AUTOLOAD routine. The name is not passed as an ordinary argument because, er, well, just because, that's why. ๐
As an exception, a method call to a nonexistentimportorunimportmethod is just skipped instead. Also, if the AUTOLOAD subroutine is an XSUB, there are other ways to retrieve the subroutine name. See "Autoloading with XSUBs" in perlguts for details.
Lots of AUTOLOAD routines load in a definition for the requested subroutine using eval(), then execute that subroutine using a special form of goto() that erases the stack frame of the AUTOLOAD routine without a trace. (See the source of the standard module documented in AutoLoader, for example.) But an AUTOLOAD routine can also just emulate the routine and never define it. ๐
For example, let's pretend that a function that wasn't defined should just invoke system with those arguments. All you'd do is:
sub AUTOLOAD {
our $AUTOLOAD; # keep 'use strict' happy
my $program = $AUTOLOAD;
$program =~ s/.*:://;
system($program, @_);
}
date();
who();
ls('-l');
And actually, if you predeclare the functions you want to call that way, you don't even need parentheses:
use subs qw(date who ls);
date;
who;
ls '-l';
A more complete example of this is the Shell module on CPAN, which can treat undefined subroutine calls as calls to external programs. ๐ฅ
There are mechanisms to help module writers split their modules into autoloadable files. See the standard AutoLoader module described in AutoLoader and in AutoSplit, the standard SelfLoader modules in SelfLoader, and the document on adding C functions to Perl code in perlxs.
๐ Subroutine Attributes ๐
A subroutine declaration or definition may have a list of attributes associated with it. If that attribute list is present, it gets broken up at space or colon boundaries and treated as though a use attributes had been seen. See attributes for details on what attributes are currently supported. And unlike the limitation with the obsolescent use attrs, the sub : ATTRLIST syntax works to associate the attributes with a pre-declaration, not just with a subroutine definition. ๐
The attributes must be valid as simple identifier names (no punctuation other than the _ character, bestie). They may have a parameter list appended, which is only checked for whether its parentheses (, ) nest properly.
Examples of valid syntax (even though the attributes are unknown):
sub fnord (&\%) : switch(10,foo(7,3)) : expensive;
sub plugh () : Ugly('\(") :Bad;
sub xyzzy : _5x5 { ... }
Examples of invalid syntax:
sub fnord : switch(10,foo(); # ()-string not balanced
sub snoid : Ugly('('); # ()-string not balanced
sub xyzzy : 5x5; # "5x5" not a valid identifier
sub plugh : Y2::north; # "Y2::north" not a simple identifier
sub snurt : foo + bar; # "+" not a colon or space
The attribute list is passed as a list of constant strings to the code which associates them with the subroutine. Specifically, that second example of valid syntax above currently looks like this in terms of how it's parsed and invoked:
use attributes __PACKAGE__, \&plugh, q[Ugly('\(")], 'Bad';
For further details on attribute lists and their manipulation, see attributes and Attribute::Handlers. ๐ธ
๐ SEE ALSO ๐
- See "Function Templates" in perlref for more about references and closures. ๐ซถ
- See perlxs if you'd like to learn about calling C subroutines from Perl.
- See perlembed if you'd like to learn about calling Perl subroutines from C.
- See perlmod to learn about bundling up your functions in separate files.
- See perlmodlib to learn what library modules come standard on your system.
- See perlootut to learn how to make object method calls. ๐
And that's a wrap on PERLSUB(1perl) bestie!! This iconic little doc is from perl v5.44.0, dated 2026-10-17 โ go forth and write subs, autoload, and override responsibly. no cap, you ate. ๐โจ๐
๐ฆ where this page comes from
- arch rolling: perl 5.44.0-1 ยท Artistic-1.0-Perl AND GPL-1.0-or-later
- ๐ girlified by deepseek-ai/DeepSeek-V4.1-Flash on : a language model's rewrite of the original, under its terms