Because Perl's mechanism for passing arguments to subroutines is a single list, arguments are positional. This makes it hard to provide default values. Some built-ins (e.g. substr
) handle this by ordering arguments according to how likely they are to be used -- less frequently used arguments appear at the end and have useful defaults.
A cleaner way to do this is by using named arguments. Perl doesn't support named arguments per se, but you can emulate them with hashes:
use 5.010; # for //
sub hello {
my %arg = @_;
my $say = delete $arg{say} // 'Hello';
my $to = delete $arg{to} // 'World!';
print "$say $to\n";
}
hello(say => 'Hi', to => 'everyone'); # Hi everyone
hello(say => 'Hi'); # Hi world!
hello(to => 'neighbor Bob'); # Hello neighbor Bob
hello(); # Hello world!
Note: The defined-or operator //
was added in Perl v5.10. It's more robust than using a logical or (||
) as it won't default on the logically false values ''
and 0
.