thpfft has asked for the wisdom of the Perl Monks concerning the following question:

so i'm reading through tom christiansen's perl style guide the other day, since i'm going to release a couple of projects into the community soon and it's just possible that people will, you know, look at them.

I get to slide 18, and encounter this:

Consider finding the union and intersection of two unique arrays @a an +d @b: foreach $e (@a) { $union{$e} = 1 } foreach $e (@b) { if ( $union{$e} ) { $isect{$e} = 1 } $union{$e} = 1; } @union = keys %union; @isect = keys %isect; This would be more idiomatically written as: foreach $e (@a, @b) { $union{$e}++ && $isect{$e}++ } @union = keys %union; @isect = keys %isect;

Idiomatic yes, working no. As far as i can see, but i can't quite bring myself to contradict the great man. %isect and %union are going to be the same, surely? the last line needs to be something like:

$isect{$_} > 1 && push(@isect,$_) for keys %isect;

but more stylish. Please would someone correct me if i've misunderstood?

Replies are listed 'Best First'.
Re: mistake in style guide?
by danger (Priest) on May 24, 2001 at 18:05 UTC

    They won't be the same (which you could check by running it with sample arrays). Take another look at the foreach block ... there's a logical AND in there, meaning the second operation will only be performed if the first was true -- and the first is true only when a previously seen key waltzes through the loop. Thus %union will contain every element in both arrays, but %isect will only contain elements common to both arrays (the arrays are assumed to be unique).

      thank you. i completely forgot about ++x and x++. stupid boy. useful lesson.