B
Brad Baxter
In the synopsis of perlsub, it says the following:
To define an anonymous subroutine at runtime:
$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
Then later is this:
Prototypes
Perl supports a very limited kind of compile-time argument
checking using function prototyping. If you declare
sub mypush (\@@)
then "mypush()" takes arguments exactly like "push()"
does. The function declaration must be visible at compile
time. The prototype affects only interpretation of new-
style calls to the function, where new-style is defined as
not using the "&" character. In other words, if you call
it like a built-in function, then it behaves like a built-
in function. If you call it like an old-fashioned subrou-
tine, 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 "$sub-
ref->()".
That last sentence seems somewhat contradictory to the
synopsis, because if prototypes have no influence on indirect
subroutine calls, then why be able to define them for anonymous
subroutines? For example:
.... as expected
.... as expected
.... as expected
.... expected an error, but prototype ignored?
-e line 1, at end of line
.... as expected
.... prototype ignored
So a couple of questions:
1. If prototypes are ignored for anonymous subroutines,
why be able to define them?
2. Am I missing a calling convention that does not ignore
them?
To define an anonymous subroutine at runtime:
$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
Then later is this:
Prototypes
Perl supports a very limited kind of compile-time argument
checking using function prototyping. If you declare
sub mypush (\@@)
then "mypush()" takes arguments exactly like "push()"
does. The function declaration must be visible at compile
time. The prototype affects only interpretation of new-
style calls to the function, where new-style is defined as
not using the "&" character. In other words, if you call
it like a built-in function, then it behaves like a built-
in function. If you call it like an old-fashioned subrou-
tine, 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 "$sub-
ref->()".
That last sentence seems somewhat contradictory to the
synopsis, because if prototypes have no influence on indirect
subroutine calls, then why be able to define them for anonymous
subroutines? For example:
12perl -le'sub n($$){print@_};n(1,2)'
.... as expected
Too many arguments for main::n at -e line 1, at end of lineperl -le'sub n($){print@_};n(1,2)'
.... as expected
12perl -le'$an=sub ($$){print@_};$an->(1,2)'
.... as expected
12perl -le'$an=sub ($){print@_};$an->(1,2)'
.... expected an error, but prototype ignored?
Type of arg 1 to main::n must be array (not single ref constructor) atperl -le'sub n(\@){print$_[0][0]};n([1,2])'
-e line 1, at end of line
.... as expected
1perl -le'$an=sub (\@){print$_[0][0]};$an->([1,2])'
.... prototype ignored
So a couple of questions:
1. If prototypes are ignored for anonymous subroutines,
why be able to define them?
2. Am I missing a calling convention that does not ignore
them?