in reply to postfix incrementing of hash slice

Consider:

%hash; # a hash $hash{$foo} = 'bar'; # used in scalar context @ary = qw(foo bar baz); $hash{@ary}++; # key is scalar(@ary) here: $hash{3} == 1; @hash{@ary} = (1,2,3); # hash is now (foo=>1,bar=>2,baz=3) @hash{@ary}++; # $hash{baz} == 4; # why?

What you want is

@hash{@array} = (1) x scalar(@array);

If you use a hash slice, you use the hash in list context. So assign it a list.

<update> If you say @hash{@ary}++, the hash iterator points to the hash key corresponding to the last element of @ary after the slice has been set up. The value of that key is incremented. </update>

<update> fixed typo (better: bug, negligence) at x - thanks cdarke ;-)
fixed another typo in first code block </update>

--shmem

_($_=" "x(1<<5)."?\n".q·/)Oo.  G°\        /
                              /\_¯/(q    /
----------------------------  \__(m.====·.(_("always off the crowd"))."·
");sub _{s./.($e="'Itrs `mnsgdq Gdbj O`qkdq")=~y/"-y/#-z/;$e.e && print}

Replies are listed 'Best First'.
Re^2: postfix incrementing of hash slice
by cdarke (Prior) on Oct 01, 2006 at 11:12 UTC
    This might be a typo in shmem's code, but the value '1' should be in list context. There is no need for 'scalar' since the rhs of the x operator can only be a numeric scalar. So I prefer:
    @hash{@array} = (1) x @array;
    With a suitable comment, since it is not particularly obvious.
      Note that this is one of the few places where adding () changes context - and I prefer to think of it as list-context ()x being a different operator than x. AIUI this is fixed in perl6 to actually have have different characters for the two operators.