here::declare - easily declare compile time variables
version 0.03
use here::declare; use const qw($ONE 1 $TWO 2); use my [qw(x y z)] => [$ONE + $TWO, 4, 5]; use our '@foo' => [$x, $y, $z];
is equivalent to:
our ($ONE, $TWO); BEGIN { *ONE = \'1'; *TWO = \'2'; } my ($x, $y, $z); BEGIN { ($x, $y, $z) = ($ONE + $TWO, 4, 5); } our @foo; BEGIN { @foo = ($x, $y, $z); }
without all that tedious typing.
all aspects of here::declare must normally be imported using use ...; statements.
here::declare
use ...;
without arguments, an initial use here::declare; line creates all five pseudo-modules ( my our state const const2 ). if you only want some, pass a list of those.
use here::declare;
my our state const const2
in the following examples, the use my declaration will be used. its usage is equivalent to use our and use state .
use my
use our
use state
=
use my '$x = 1'; use my '($y, $z) = (2, 3)';
this is the simplest transform, which given an argument matching foo = bar gets rewritten as:
foo = bar
my foo; BEGIN {foo = bar}
so the above becomes:
my $x; BEGIN {$x = 1} my ($y, $z); BEGIN {($y, $z) = (2, 3)}
while this version looks the closest to perl's native variable declarations, it is unable to pass arguments that can not easily be written in a string.
use my '$say' => sub {print @_, $/}; use my '@array' => [1, 2, 3], '%hash' => {a => 1, b => 2};
here an arbitrarily long list of name/value pairs is passed to the declarator.
if the name is a $scalar then the corresponding value will be copied into the newly created variable at compile time. it is safe to pass any type of scalar as a value, and it will not be stringified. bareword and -bareword names will be interpreted as $bareword which can cut down on the number of quotes you need to write (use my say => sub {...};)
$scalar
bareword
-bareword
$bareword
use my say => sub {...};
if the name is an @array or %hash the corresponding values must be ARRAY or HASH references, which will be dereferenced and copied into the new variables.
@array
%hash
ARRAY
HASH
my $say; BEGIN {$say = here::fetch(1)} my @array; BEGIN {@array = @{here::fetch(2)}} my %hash; BEGIN {%hash = %{here::fetch(3)}}
where here::fetch is a subroutine that returns the values passed into the declarator, which gets around needing to serialize the values.
here::fetch
use my [qw($x $y $z)] => 1, 2, 3; use my [qw($foo @bar %baz)] => ['FOO', [qw(B A R)], {b => 'az'}];
this usage is exactly like the list of name/value pairs usage except the names and values are passed in separately. the names must be an array reference. the values can be an array reference or a list.
as a syntactic shortcut, the above two lines could also be written:
use my '($x, $y, $z)' => 1, 2, 3; use my '($foo, @bar, %baz)' => 'FOO', [qw(B A R)], {b => 'az'};
which of course expands to something equivalent to:
my ($x, $y, $z); BEGIN {$x = 1; $y = 2; $z = 3} my ($foo, @bar, %baz); BEGIN {$foo = 'FOO'; @bar = qw(B A R); %baz = (b => 'az')}
ignoring the complexities of here::fetch
use const '$FOO' => 'BAR'; use const2 DEBUG => 1;
which expands to:
our $FOO; BEGIN {*FOO = \'BAR'} sub DEBUG () {1} our $DEBUG; BEGIN {*DEBUG = \DEBUG}
these declarations only accept $scalar , bareword or -bareword names (interchangeably), but otherwise the usage is similar to use my ...
use my ...
the single argument syntax is not supported with these two declarations.
you can remove the pseudo-modules manually:
no here::declare;
or let the declaration fall out of scope if B::Hooks::EndOfScope is installed:
{ use here::declare; use my ...; # works } use my ...; # error
if you don't like the installation of pseudo-modules, you can pass use here::declare a list of any of the pseudo-module names each containing at least one upper case character. this will cause that name to be exported into your namespace as a subroutine.
use here::declare
use here::declare 'MY'; use here MY [qw($x $y)] => [0, 0];
here::declare is built on top of the " here " framework.
in writing this module, I was pushed by p5p to make the interface a bit closer to the native my and our keywords. I did this with Devel::Declare in Begin::Declare. Begin::Declare is certainly closer in usage to the keywords, but the dependency on Devel::Declare might prevent installation for some people. in addition, this module (despite using Filter::Util::Call) is a little safer to use than Begin::Declare since the use statement required by this module more clearly delineates the scope of its actions.
my
our
Begin::Declare
Devel::Declare
Filter::Util::Call
use
Eric Strom, <asg at cpan.org>
<asg at cpan.org>
please report any bugs or feature requests to bug-here at rt.cpan.org, or through the web interface at http://rt.cpan.org/NoAuth/ReportBug.html?Queue=here. I will be notified, and then you'll automatically be notified of progress on your bug as I make changes.
bug-here at rt.cpan.org
copyright 2011 Eric Strom.
this program is free software; you can redistribute it and/or modify it under the terms of either: the GNU General Public License as published by the Free Software Foundation; or the Artistic License.
see http://dev.perl.org/licenses/ for more information.
1 POD Error
The following errors were encountered while parsing the POD:
L<> starts or ends with whitespace
To install here, copy and paste the appropriate command in to your terminal.
cpanm
cpanm here
CPAN shell
perl -MCPAN -e shell install here
For more information on module installation, please visit the detailed CPAN module installation guide.