Beefy Boxes and Bandwidth Generously Provided by pair Networks
Perl: the Markov chain saw
 
PerlMonks  

Re^2: grep for hash?

by rovf (Priest)
on Jul 07, 2009 at 15:02 UTC ( [id://777900]=note: print w/replies, xml ) Need Help??


in reply to Re: grep for hash?
in thread grep for hash?

I was surprised that this not only works, but also does not complain if strictures are added to the code.

The code looks ingenious, but I wonder about two aspects: First, you are accessing a list one time as a hash via %NAME, and then the same list as an array, via @NAME. Is this considered accepted practice? Honestly, I hadn't expected it to work with lexically scoped variables, and I'm not sure whether this trick (if I can call it like this) will remain with later Perl versions.

A more serious problem is the line
@new{ @keys } = @orig{ @keys = grep /[adf]/, keys %orig };
where you rely on the fact that @keys gets its value first (from the grep) before it is used to form a slice for @new. I think this is undefined behaviour, isn't it?
-- 
Ronald Fischer <ynnor@mm.st>

Replies are listed 'Best First'.
Re^3: grep for hash?
by Fletch (Bishop) on Jul 07, 2009 at 15:25 UTC

    All of the references are to the hashes %new and %old; the leading @ and curlies is just the way you name slices. The only array involved in the whole thing is @keys.

    As for relying on the ordering, I think it's pretty safe to count that the rvalue will be computed and available before the lvalue is populated with it.

    The cake is a lie.
    The cake is a lie.
    The cake is a lie.

      I think it's pretty safe to count that the rvalue will be computed and available before the lvalue is populated with it.

      In general, no. The container can be placed on the stack before the value it will receive. The assignment only occurs after both the value and the container are on the stack.

      In Perl, operands are always evaluated from left to right, except the operands for assignment operators are always evaluated from right to left. But that's not documented.

      GivenDisinguishes these Interpretations
      Operator Precedence1+2*3(1+2)*3
      -vs-
      1+(2*3)
      Operator Associativity2**3**4(2**3)**4
      -vs-
      2**(3**4)
      Operand Evaluation Orderfoo()+bar()foo() -> bar() -> add
      -vs-
      bar() -> foo() -> add

      Update: I foresaw confusion between operator associativity and operand evaluation order, so I added the table.

        It's not explicitly documented but it's stated in perlsyn that the assignment operator works "as in C", and it has the same right-to-left associativity as C's, and the value of the assignment is itself a valid rvalue for another subsequent assignment. Granted it's not chiseled into stone tablets, but I don't think that it's a "ZOMGWTFBBQ no one knows what'll happen just don't do that" case like ++$a + $a++ is.

        That being said, your alternative with the separate assignment before use is definitely a clearer implementation.

        The cake is a lie.
        The cake is a lie.
        The cake is a lie.

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: note [id://777900]
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others musing on the Monastery: (3)
As of 2024-04-26 05:56 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found