You cannot use a list as a hash, because lists are not hashes. :)
The operator => ("bold comma") is the same as,, with an additional attribute in which it quotes left words. Therefore, when you write this:
( a=>0, b=>1, c=>2 )
This is exactly the same as this:
( 'a', 0, 'b', 1, 'c', 2 )
And this is not a hash, it's just a list.
Lists are ephemeral things that live on the stack; as you rightly point out, they can be assigned to both arrays and hashes, but they do not match arrays and hashes.
Before it can be used, a hash must be created. Each key / value list assigned to it requires that key hashing and allocated buckets, as well as values, are placed in buckets. Therefore, when you write:
$foo = {a=>0, b=>1, c=>2}->{c};
What's happening:
- Items in the list ('a', 0, 'b', 1, 'c', 2) are pushed onto the stack
- An anonymous hash built by the
{ LIST } operator - List items are unloaded from the stack and assigned to the hash, turning them into keys and values
- A link to this hash is returned.
- Link is dereferenced by operator
-> - The
c key is scanned and - Return value, decreasing expression to
$foo = 2
So why can you write (qw(abc))[2] if the list is not an array? Well, internally the stack is just an SV * array, so I suppose the indexing ability was simple and seemed like a good idea.
Here's an article by a really cool guy that you might also find instructive: Arrays vs. Lists in Perl: What's the Difference?