2

In this piece of code, shift is used twice, even though the method only takes one parameter:

sub regexVerify ($)
{
   my $re = shift;

   return sub
   {
      local $_ = shift;
      m/$re/ ? $_ : undef;
   };
}

What does this make the value of local $_, once shift is used again? I was (perhaps naively) assuming that shifting into nothingness would result in undef. But if that were true, this line has no meaning, right?:

m/$re/ ? $_ : undef;

The above sub is called like:

regexVerify (qr/^([a-z].*)?$/i);
CptSupermrkt
  • 6,844
  • 12
  • 56
  • 87

2 Answers2

2

The second shift is inside the inner sub declaration. That scope will have an entirely new @_ to work with, which won't have anything to do with the @_ passed to the outer subroutine.

regexVerify is a subroutine that returns another subroutine. Presumably you would later invoke that subroutine with an argument:

my $func = regexVerify(qr/^([a-z].*)?$/i);
# $func is now a "code reference" or "anonymous subroutine"

...

if ($func->($foo)) {    # invoke the subroutine stored in $func with arg ($foo)
    print "$foo is verified.\n";
} else {
    print "$foo is not verified!\n";
}
mob
  • 117,087
  • 18
  • 149
  • 283
  • That makes sense, but I still don't get it --- if the inner sub takes no parameters, what is local $_ being initialized as, if not undef? – CptSupermrkt Jun 05 '13 at 20:26
  • @CptSupermrkt The inner sub *does* take parameters, re-read mob's answer. `regexVerify` returns a sub, which is then invoked like `$func->($This_Is_A_Parameter)`! – amon Jun 05 '13 at 20:35
  • It does take a parameter, `$foo` in the example. – ikegami Jun 05 '13 at 20:35
2

local $_ = shift; doesn't get executed until you make call to anonymous function. ie

my $anon_func = regexVerify (qr/^([a-z].*)?$/i);

# NOW sending arguments in @_ for local $_ = shift;
print $anon_func->("some string"); 
mpapec
  • 50,217
  • 8
  • 67
  • 127