Retrieving arguments to a subroutine with shift
A subroutine's arguments come in via the special @_
array.
The shift
without an argument defaults to @_
.sub volume { my $height = shift; my $width = shift; my $depth = shift; return $height * $width * $depth; }
Assign arguments to a subroutine with list assignment
You can also assign arguments en masse with list assignment:sub volume { my ($height, $width, $depth) = @_; return $height * $width * $depth; }
Handle arguments directly by accessing @_
In some cases, but we hope very few, you can access arguments directly in the @_
array.sub volume { return $_[0] * $_[1] * $_[2]; }
Arguments passed can get modified
The arguments passed to a subroutine are aliases to the real arguments.my $foo = 3; print incr1($foo) . "\n"; # prints 4 print "$foo\n"; # prints 3 sub incr1 { return $_[0]+1; }This can be good if you want it to be:
sub incr2 { return ++$_[0]; }
Subroutines have no argument checking
You can pass any anything to a subroutine that you want.sub square { my $number = shift; return $number * $number; } my $n = square( 'Dog food', 14.5, 'Blah blah blah' );Only the first argument is used by the function. For that matter, you can call the function with any number of arguments, even no arguments:
my $n = square();and Perl won't complain.
The module Params::Validate solves many of these validation problems.
Perl has "prototypes". Ignore them.
Somewhere along the way, prototypes got added, so you can do things like this:sub square($) { ... } my $n = square( 1, 2, 3 ); # run-time errorHowever, don't use them. They don't work on objects, and they require that the subroutines be declared before they're called. They're a nice idea, but just not practical.
Make things happen at compile time with the BEGIN
block
BEGIN
is a special type of code block. It allows
programmers to execute code during Perl's compile phase, allowing for
initializations and other things to happen.Perl uses
BEGIN
any time you use
a module; the following two statements are equivalent:use WWW::Mechanize; BEGIN { require WWW::Mechanize; import WWW::Mechanize; }
Pass in arrays and hashes as references
Remember that the parameters passed into a subroutine are passed as one big array. If you do something like the following:my @stooges = qw( Moe Larry Curly ); my @sandwiches = qw( tuna ham-n-cheese PBJ ); lunch( @stooges, @sandwiches );Then what's passed in to
lunch
is the list( "Moe", "Larry", "Curly", "tuna", "ham-n-cheese", "PBJ" );Inside
lunch
, how can you tell where the stooges end and the sandwiches begin? You can't. If you try this:sub lunch { my (@stooges, @sandwiches) = @_;then all six elements go into
@stooges
and @sandwiches
gets nothing.The answer is to use references, as in:
lunch( \@stooges, \@sandwiches ); sub lunch { my $stoogeref = shift; my $sandwichref = shift; my @stooges = @{$stoogeref}; my @sandwichref = @{$sandwichref}; ... }
No comments:
Post a Comment