<update> The same question, with several good answers: Modifying hash keys via aliasing </update>
The best I can do at the moment is this quote from perlref - although your question is really about aliases and not "hard" references, so I may be off here.
As a special case, \(@foo) returns a list of references to the contents of @foo, not a reference to @foo itself. Likewise for %foo, except that the key references are to copies (since the keys are just strings rather than full-fledged scalars).
Also, note that the behavior when passed a hash (which is kind of unusual BTW, why do you want to do that?) is consistent between chomp and a custom sub.
use warnings;
use strict;
use Data::Dump;
sub antichomp (@) {
for (@_) {
$_ .= $/;
}
}
my %hash = (x=>'Hello',y=>'World!');
antichomp(%hash);
dd \%hash;
%hash = ("x\n"=>"Hello\n","y\n"=>"World!\n");
chomp(%hash);
dd \%hash;
__END__
{ x => "Hello\n", y => "World!\n" }
{ "x\n" => "Hello", "y\n" => "World!" }
prototype("CORE::chomp") does return undef, indicating that there isn't an exact equivalent, but I do think that you can get pretty close.
As for all the other behaviors, at least those are defined:
Hashes in list context return a list of their key/value pairs. Excerpts from perldata:
... hashes included as parts of other lists (including parameters lists and return lists from functions) always flatten out into key/value pairs.
LISTs do automatic interpolation of sublists. That is, when a LIST is evaluated, each element of the list is evaluated in list context, and the resulting list value is interpolated into LIST just as if each individual element were a member of LIST. Thus arrays and hashes lose their identity in a LIST--the list
(@foo,@bar,&SomeSub,%glarch)
contains all the elements of @foo followed by all the elements of @bar, followed by all the elements returned by the subroutine named SomeSub called in list context, followed by the key/value pairs of %glarch.
The behavior of foreach loops in regards to the iterator variable is defined in perlsyn:
The foreach loop iterates over a normal list value and sets the scalar variable VAR to be each element of the list in turn. ... the variable is implicitly local to the loop and regains its former value upon exiting the loop. ... This implicit localization occurs only in a foreach loop. ... If VAR is omitted, $_ is set to each value.
If any element of LIST is an lvalue, you can modify it by modifying VAR inside the loop. ... In other words, the foreach loop index variable is an implicit alias for each item in the list that you're looping over.
Arguments to subroutines are also aliases to the original values, as long as you access the elements of @_ directly, without first doing the typical assignment like my ($x,$y) = @_; or my $x = shift;. From perlsub:
Any arguments passed in show up in the array @_. ... The array @_ is a local array, but its elements are aliases for the actual scalar parameters. In particular, if an element $_[0] is updated, the corresponding argument is updated (or an error occurs if it is not updatable). ... Assigning to the whole array @_ removes that aliasing, and does not update any arguments.
Prototypes are discussed in perlsyn, and it's easy enough to test and see the same behavior of hashes flattening into a list of unordered key/value pairs here too:
use warnings;
use strict;
use Data::Dump;
sub foo (@) { dd \@_ }
my %hash = (x=>'Hello',y=>'World!');
foo(%hash);
__END__
["y", "World!", "x", "Hello"]
|