Reputation: 11329
I have an input file with 3 columns, and I wanted to print lines where the 3rd column hasn't been duplicated. so if my input data looks like this:
0,1,abc
0,2,abc
0,5,xyz
I would print:
0,1,abc
0,5,xyz
I initially started with the below, but it didn't produce any output. what am I doing wrong in this line?
perl -ne '/^[0-9]+,[0-9]+,(.+)/ && ++$a{$1} && print "$_ $a{$1}\n" if $a{$1}>0'
please note that I'm not looking for a solution to my problem, as I coded it in a different way. but I am interested in why the above line doesn't do what I expect, as it exposes a gap in my perl understanding.
Upvotes: 2
Views: 227
Reputation: 3734
perl -ne 'print "$_ $a{$1}\n" if /^[0-9]+,[0-9]+,(.+)/ && !$a{$1}++'
Upvotes: 0
Reputation: 33
perl -ne '/^[0-9]+,[0-9]+,(.+)/ && ++$a{$1} ;print "$_" if $a{$1}==1'
What you posted, had also included printing the value of $a{$1}. I assume that was for debug.
I took out the "\n" because there is already a line feed in $1.
If you want to change that, use chomp at the beginning of the line.
Although using the && in a single line is nifty, I think it would be good advice to try and write the perl in a real formatted block. This would help you learn better, and debug easier.
Looking at your line, it is not immediately easy to see what the true intention of
print $_ if $a{$1}>0
A better approach for learning ( In my opinion ) would have been something similar to this:
perl -ne '/^[0-9]+,[0-9]+,(.+)/ and do{
if ( ! exists $a{$1} ){
print "$_";
};
$a{$1}=1;
}'
Upvotes: 0
Reputation: 118595
For one thing, the postfix if $a{$1} > 0
expression gets evaluated first, as if you said
if ($a{$1} > 0) {
/^"[0-9]+","[0-9]+","(.+)"/ && ++$a{$1} && print "$_ $a{$1}\n"
}
but $a{...}
(and $1
) will only get updated inside the if
block, so the if
statement is never true.
For another thing, your regex has double quote characters but your sample input doesn't. Was that a typo?
Upvotes: 2