Operating System - HP-UX
1826301 Members
4131 Online
109692 Solutions
New Discussion

Re: awk problem...any hints??

 
SOLVED
Go to solution
amonamon
Regular Advisor

awk problem...any hints??

Hello I have one problem..

I have fileA:

value1 1
value2 3
value3 4
value1 9
value2 5
value5 5
value1 2
value4 1
...
..
...
..


I wanted file like this:

fileB:
value1 12 3
value2 3 2
value3 4 4
value4 1 1
value5 5 1


where I do not have douplicates anymore and second column is sum of values for each value and 3. column is number each same record shows in file

for example in fileA 3 times value1 records is shown..
vale2 is 2 times shown in fileA and 2 solumn in fileB meand that total values for value1 is 12



any hints?
6 REPLIES 6
H.Merijn Brand (procura
Honored Contributor

Re: awk problem...any hints??

# perl -le'/^(\S+)\s+(\S+)/&&push%{$v{$1}},$2}END{print"$_:@{$v{$_}}"for sort keys%v' fileA

untested

Enjoy, Have FUN! H.Merijn
Enjoy, Have FUN! H.Merijn
amonamon
Regular Advisor

Re: awk problem...any hints??

woowww...I understand nothing here...:) but thanks for answer..is ther a way to to that with awk??
I am newbie here..
H.Merijn Brand (procura
Honored Contributor
Solution

Re: awk problem...any hints??

And wrong also. Small typo.

lt09:/home/merijn 106 > perl -nle'/^(\S+)\s+(\S+)/&&push@{$v{$1}},$2;}END{print"$_:@{$v{$_}}"for sort keys%v' fileA
value1:1 9 2
value2:3 5
value3:4
value4:1
value5:5
lt09:/home/merijn 107 >

My awk foo lets me down on this, but lemme try to explain what I did

> perl -nle

-n process for every line, but do not print
-l add a newline to every printed line
-e the `script' expression

> /^(\S+)\s+(\S+)/

match the line as

^ start of line
(\S+) non-whitespace (as many as matched. The parens capture the result in $1 (e.g. value1)
\s+ whitespace
(\S+) non-whitespace (e.g. 12)

> && push @{$v{$1}}, $2;

if it matches, push the second arg $2 onto a list grouped in hash %v (which is just a short arbitrary name) indexed with the value from $1

> } END {

That is a bit mean. You should know about how perl invokes with -n and -p to use this, but effectively, the next block is only invoked after all input is processed

> print "$_:@{$v{$_}}" for sort keys%v

the keys of the hash are the values found, which we iterate over with for keys %v
Those keys are processed by sort and then used in the print
the print prints the key (the value from fileA), and the list of numebrs collected in the process after that. The calling -l option will add a newline

Hopes that might motivate you to use perl more often

Enjoy, Have FUN! H.Merijn
Enjoy, Have FUN! H.Merijn
spex
Honored Contributor

Re: awk problem...any hints??

amonamon,

Here's an awk script I wrote that totals a day's worth of sessions from Oracle's listener.log (after it's run through 'sed'). It it very similar to what you're looking for, and should be relatively easy to modify:

# more acc.awk
BEGIN {
FS=","
hr=-1
d=-1
ptr=0
}
{
if (hr==-1 || hr==$2)
{
if (nb[$3]==null)
{
na[ptr]=$3
ptr++
}
nb[$3]++
}
else
{
printf("********* %d:00 to %d:59 on %s *********\n",hr,hr,d)
for (i=0; i {
printf("%30s\t\t%d\n",na[i],nb[na[i]])
}
for (i in na)
delete na[i]
for (i in nb)
delete nb[i]
ptr=0
}
d=$1
hr=$2
}
END {
printf("********* %d:00 to %d:59 on %s *********\n",hr,hr,$1)
for (i=0; i {
printf("%30s\t\t%d\n",na[i],nb[na[i]])
}
}


It gives output of the form:

********* 6:00 to 6:59 on 03-JUL *********
user2 7
oracle 14
user1 10
Sandman!
Honored Contributor

Re: awk problem...any hints??

Hello amonamon...here's an awk construct that does what you're looking for:

# awk '{x[$1]++;z[$1]+=$2} END{for(i in x) print i,z[i],x[i]}' fileA > fileB

~cheers
amonamon
Regular Advisor

Re: awk problem...any hints??

thanks everyone for help..that help me solve my problem :)

cheers,