--- David Blevins <[EMAIL PROTECTED]> wrote:
> >   perl -nle 'print if !$seen{$_}++'
> 
> The dash n (-n) puts the command 'print if !$seen{$_}++' in a while
> (<>) { ... } loop.  So we get:
> 
> while (<>) {
>     print if !$seen{$_}++
> }
> 
> $seen{$_}
> 
> Tries to lookup the line in the hash of lines we've already seen.
> 
> $seen{$_}++
> 
> This is a complete guess, I can't seem to find anything like this in
> the 'Programming Perl' book.

It's just a postfix increment on the value in %seen as looked up using
$_ as the key. You've got the idea.

> It seems that if you say:
> 
> $seen{$_} = 1;
> 
> it causes the key to be added to the hash with the value 1, which is
> true in boolean context.
> So, if the key (line) wasn't previously seen, line"
> 
> $seen{$_}
> 
> might return a 0 or "false" to indicate it wasn't found.  Then the
> line
> 
> $seen{$_}++
> 
> might take that 0/"false", increment it by one turning it to 1/"true"
> causing the key/$_/"line" to be added with a value of 1/"true".  If
> the $_/"line" were already seen, it would have been added initially
> with a value 1/"true"; the ++ in this situation would just increment
> the value to 2,3,4...n, all of which are "true" values.

There you go.

> !$seen{$_}
> 
> Might negate the 1/"true" return of looking up a key that previously
> existed in the hash, causing the
> 
> print
> 
> statement to execute, which is just short for
> 
> print STDOUT $_;

Good. The leading ! makes it boolean, so it returns 1 or ''.
 
> So how close am I and where can I read about this?

lol -- you kind of have to look up the pieces. ;o]
Or maybe there's something in the FAQ's?

> > perl -pe '$_ x= !$seen{$_}++'
> 
> This would bypass the need for the print statement, but I'm not sure
> how the '$_ x= ' in the statement works.

This is the one that tickled me most.
I parsed it in another post. ;o]

> >   $seen{$_} ||= print OUT while <IN>;
> 
> This is tons of fun!  Dying to know the answer!

 ||= is an "or-equal" -- it assigns the right-hand argument to the
left-hand argument if the current value of the left-hand argument is
boolean false. "$a ||= 1" assigns 1 to $a if $a was '',0, or undef.
Otherwise it leaves it alone.

Since print returns a bool, and while <IN> assigns to $_ (which is
print()'s default), it prints the line just read and assigns 1 to
$seen{$_} if $seen{$_} had no value, but if $seen{$_} already has a
value, it just returns that in a void context -- a no-op. =o)
Then it reads the next line of <IN>.

I love Perl. =o)

Of course, writing readable code is always a good idea, but explaining
*tight* code is a great learning experience! lol!

__________________________________________________
Do You Yahoo!?
Make international calls for as low as $.04/minute with Yahoo! Messenger
http://phonecard.yahoo.com/

-- 
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]

Reply via email to