lexica...erscore(3pm)

πŸ‘‘ NAME πŸ‘‘

lexical::underscore β€” bestie, this lets you peek at your caller's lexical $_ and honestly? iconic.


✨ SYNOPSIS ✨

use 5.010;
use lexical::underscore;
use Test::More;

sub is_uppercase {
   my $var = @_ ? shift : ${lexical::underscore()};
   return $var eq uc($var);
}

my $thing = 'FOO';
my $works = 0;

given ( $thing ) {
   when ( is_uppercase ) { $works++ }
}

ok($works);
done_testing();

πŸ’– DESCRIPTION πŸ’–

okay so, plot twist: starting with Perl 5.10, you can make a lexical version of the Perl default variable $_. Some Perl constructs β€” like the given keyword β€” just automatically use a lexical $_ instead of the global $_. no cap.

And sometimes it's genuinely useful for a sub to reach into its caller's $_ variable, no matter whether that thing was lexical or not. The official, canon way to do this is the (_) sub prototype. but bestie, there are disadvantages: it can only show up as the final required argument in a prototype, and the sub has literally zero way of telling apart an explicitly passed argument from $_. πŸ’€

This caused the author problems with Scalar::Does, because they wanted the does function to be callable as either:

does($thing, $role);
does($role);  # assumes $thing = $_

With _ in the prototype, $_ got passed to the function at the end of its argument list β€” so effectively does($role, $thing) β€” which made it impossible to tell which argument was the role. 😭

Enter lexical::underscore, which lets you grab your caller's lexical $_ variable as easily as:

${lexical::underscore()}

And you can reach lexical $_ further up the call stack like this:

${lexical::underscore($level)}

If you happen to ask for $_ at a level where there's no lexical $_ available, you get the global $_ instead. consolation prize πŸŽ€

Also, heads up: this module does work on Perl 5.8, but since there's no lexical $_ there, it always returns the global $_.

🧚 Technical Details 🧚

The lexical::underscore function returns a scalar reference to either a lexical $_ variable somewhere up the call stack (it's giving PadWalker magic ✨) or to the global $_ if there was no lexical version to be found.

Wrapping lexical::underscore in ${ ... } dereferences that scalar reference, which is what lets you access it β€” and even assign to it. slay.


πŸ’€ BUGS πŸ’€

Found a bug? Please report any bugs to <http://rt.cpan.org/Dist/Display.html?Queue=lexical-underscore>. do it for the plot.


🌈 SEE ALSO 🌈

PadWalker. that's the whole vibe, iykyk.


🫢 AUTHOR 🫢

Toby Inkster <tobyink@cpan.org>. king behavior.


This software is copyright (c) 2012, 2014 by Toby Inkster.

This is free software; you can redistribute it and/or modify it under the same terms as the Perl 5 programming language system itself.


πŸ”₯ DISCLAIMER OF WARRANTIES πŸ”₯

THIS PACKAGE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.

fr fr, no warranty, bestie. read it twice. πŸ“

that's the whole page, mwah πŸ’‹ β€” brought to you by perl v5.34.0, dated 2022-06-15, and the manual section lexical::underscore(3pm) under User Contributed Perl Documentation. go forth and access your caller's $_, queen πŸ‘‘

πŸ“¦ where this page comes from