简体   繁体   中英

Why is (a=>1,b=>2){a} a syntax error?

I want to use a hash in an expression. No problem:

use strict;
use warnings;
my %h = (a=>1, b=>2);
my $h = $h{a};
print "h='$h'\n";

But since I will refer to it only once, I don't want to name it. Naively substituting the hash content for $h doesn't work. The following code produces a syntax error on line 3 at "){":

use strict;
use warnings;
my $x = (a=>1, b=>2){a};
print "x='$x'\n";

I know that the following is the way to accomplish what I need:

use struct;
use warnings;
my $y = {a=>1, b=>2}->{a};
print "y='$y'\n";

Why doesn't the second example work?

EDIT 1: This is a MVCE. In real life, my hash key ('a' in this example) is not a constant.

EDIT 2: A little more about my motive: I don't want an unnecessary variable in scope in my code, so if I were to restrict the scope of %h to where it really belongs, I would have this:

use strict;
use warnings;
my $h;
{
    my %h = (a=>1, b=>2);
    $h = $h{a};
}
print "h='$h'\n";

I don't want to leave %h in scope for more code than I need, but it's also clunky to write the code segment with the extra block for scoping. This is why I was looking for a clean one-line way to make the assignment.

In my $x = (a=>1, b=>2){a}; , that doesn't represent a hash. It's a list with the following values: 'a', 1, 'b', 2 . The => , aka fat-comma is simply a glorified comma, with the feature that it quotes the value on the left hand side. It does not implicitly mean that we're dealing with/creating a hash. Example:

my @array = ('a' => 1 => 'b' => 2);

To get the value 1 from the original code shown, you'd have to do my $x = (a=>1, b=>2)[1]; .

The hashref method you used: my $y = {a=>1, b=>2}->{a}; is the standard way to use an anonymous hash.

See, (something1, something2, ...) is not an array constructor. It's just a way to say to interpreter that "we have something in a list context". You can understand each (a,b,c,...) usage like an assignment to an array with no name. So, yes we can get a value from this array by index. ('a' => 1, 'b' => 2)[1] will return 1 .

Hash will be created only after assignment in list context if left side is a hash variable. Before assignment we can't use this list like hash because we don't have hash. So postcircumfix operation {...} is not allowed.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM