The UNIX and Linux Forums  


Go Back   The UNIX and Linux Forums > Top Forums > Shell Programming and Scripting
.
google unix.com



Shell Programming and Scripting Post questions about KSH, CSH, SH, BASH, PERL, PHP, SED, AWK and OTHER shell scripts and shell scripting languages here.

More UNIX and Linux Forum Topics You Might Find Helpful
Thread Thread Starter Forum Replies Last Post
while loop inside while loop panknil Shell Programming and Scripting 0 01-07-2008 12:49 PM
For loop xramm HP-UX 3 10-10-2007 03:20 PM
While Loop hemangjani Shell Programming and Scripting 2 11-02-2006 11:01 AM
for loop munnabhai1 Shell Programming and Scripting 3 04-06-2006 03:30 PM
how to get the similar function in while loop or for loop trynew Shell Programming and Scripting 3 06-17-2002 12:09 PM

Closed Thread
English Japanese Spanish French German Portuguese Italian Dutch Swedish Russian Norwegian Hungarian Hebrew Danish Bulgarian Greek Powered by Powered by Google
 
LinkBack Thread Tools Search this Thread Rate Thread Display Modes
  #1 (permalink)  
Old 08-30-2007
baghera baghera is offline
Registered User
  
 

Join Date: Aug 2007
Posts: 23
While-loop with awk

How to make a while-loop with awk.

Lets say I have a variable number of columns:

1 4 3
2 4 4
3 5 3

Now I want to add all elements of column 1, 2 and 3 and then divide them by the number of elements in each.

columns= the number of columns which is given as an argument to my script

i = the column we are adding for the moment

this is some pseudo code for what I want to be done:

while [columns > 0]
do
awk '{sum+=$i} END {print sum/NR "\t"}'
i++
column--
done

So when executed the finished result will be:

2 6.5 3.333333

But I don't get my while loop to function. Please help me. This is my code:

#############################
while [ "$columns" -gt 0 ]
do
awk_cmd=`awk -v i=$1 '{sum+=$i} END {print sum/NR}'`
echo "$data | $awk_cmd"
i=`expr $i + 1`
columns=`expr $columns - 1`
done
#############################
  #2 (permalink)  
Old 08-30-2007
ranj@chn ranj@chn is offline Forum Advisor  
Playing with Ubuntu Now!
  
 

Join Date: Oct 2005
Location: Chennai
Posts: 365
will this work?


Code:
awk -f temp.awk tempfile

where temp.awk is

Code:
{ for(i=1;i<=NF;i++) { sum[i]+=$i } }
END { for (i in sum) {printf("%f\t", sum[i]/NR) } }

Quote:
Btw, the second column should not be 6.5, but 4.33

Last edited by ranj@chn; 08-30-2007 at 11:41 AM.. Reason: add comments
  #3 (permalink)  
Old 08-30-2007
vgersh99's Avatar
vgersh99 vgersh99 is online now Forum Staff  
Moderator
  
 

Join Date: Feb 2005
Location: Boston, MA
Posts: 5,131
Quote:
Originally Posted by ranj@chn View Post
Code:
awk -f temp.awk tempfile

where temp.awk is

Code:
{ for(i=1;i<=NF;i++) { sum[i]+=$i } }
END { for (i in sum) {printf("%f\t", sum[i]/NR) } }
ranj,
when iterating through an array 'sum' with the index of 'i', the order of the iteration is indeterminant, i.e. don't assume that 'i' will go from '1' to 'NF'.
  #4 (permalink)  
Old 08-30-2007
ranj@chn ranj@chn is offline Forum Advisor  
Playing with Ubuntu Now!
  
 

Join Date: Oct 2005
Location: Chennai
Posts: 365
Smile in the END?

I didnt know that. So, you mean the values could be printed in any order? Will keep that in mind!!!
  #5 (permalink)  
Old 08-30-2007
vgersh99's Avatar
vgersh99 vgersh99 is online now Forum Staff  
Moderator
  
 

Join Date: Feb 2005
Location: Boston, MA
Posts: 5,131
Quote:
Originally Posted by baghera View Post
How to make a while-loop with awk.

Lets say I have a variable number of columns:

1 4 3
2 4 4
3 5 3

Now I want to add all elements of column 1, 2 and 3 and then divide them by the number of elements in each.

columns= the number of columns which is given as an argument to my script

i = the column we are adding for the moment

this is some pseudo code for what I want to be done:

while [columns > 0]
do
awk '{sum+=$i} END {print sum/NR "\t"}'
i++
column--
done

So when executed the finished result will be:

2 6.5 3.333333

But I don't get my while loop to function. Please help me. This is my code:

#############################
while [ "$columns" -gt 0 ]
do
awk_cmd=`awk -v i=$1 '{sum+=$i} END {print sum/NR}'`
echo "$data | $awk_cmd"
i=`expr $i + 1`
columns=`expr $columns - 1`
done
#############################
baghera,
I believe we've already gone through this exercise once in one of the previous threads. What is it exactly that you're not trying to do differently?
If you're try to calculate the average value per column for all the rows - this solution has also been provided as part of the previous thread.
Try to understand the previous solution and/or adjust it to your 'new' [???] requirement.
  #6 (permalink)  
Old 08-30-2007
baghera baghera is offline
Registered User
  
 

Join Date: Aug 2007
Posts: 23
Quote:
Originally Posted by vgersh99 View Post
baghera,
I believe we've already gone through this exercise once in one of the previous threads. What is it exactly that you're not trying to do differently?
If you're try to calculate the average value per column for all the rows - this solution has also been provided as part of the previous thread.
Try to understand the previous solution and/or adjust it to your 'new' [???] requirement.
The difference between now and then is that I need it to be a bash/bourne script. The previous thread was for a awk-program. But I had to change it to be a bash/bourne shell script. To be honest, I don't know the difference really, but I got some uggly looks from my friend when I showed him the awk-program that some of you helped me with. So I turned back to bourne/bash.

So my script so far is:

cat $1 | grep "results" | grep "get numbers" | xargs -n $2

It is somewhat more advanced then the command above, but this is only so you get the whole picture. It produces columns with values from files named $1 and the numbers of columns are determined by $2.

Now, since $2 is a variable I don't know how many columns there is going to be. It is not going to be many, lets say around 2-10 should suffice. I need, as I previous stated go through each column adding them and then dividing them with the number of elements in each column. So if the output from the following command above is:

1 4
2 5
3 6
4 7
5 8

The result should be:

3 6

Which is the average of each of the columns.

I've done something like this, but it doesn't seem to work,

while [ $j > 0 ]
do
cat list | awk '{sum+=$i} END {print sum/NR}'
i=$[$i+1]
j=$[$j-1]
done

awk seems to have problem with $i. But I need this to be a variable but awk says:

awk: illegal field $(), name "i"
input record number 1, file
source line number 1

Last edited by baghera; 08-30-2007 at 03:45 PM..
  #7 (permalink)  
Old 08-31-2007
baghera baghera is offline
Registered User
  
 

Join Date: Aug 2007
Posts: 23
I solved the problem:


Code:
i="1"
j=$2

while [ "$j" -gt  0 ]
  do
  echo "$data" | awk -v k=$i '{sum+=$k} END {print sum/NR}'
  i=$[$i+1]
  j=$[$j-1]
done

This works fine for me. And to get the columns I just use:


Code:
data='cat myList | xargs -n $2'

Closed Thread

Bookmarks

Thread Tools Search this Thread
Search this Thread:

Advanced Search
Display Modes Rate This Thread
Rate This Thread:

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are On




All times are GMT -4. The time now is 04:25 PM.


Powered by: vBulletin, Copyright ©2000 - 2006, Jelsoft Enterprises Limited. Language Translations Powered by .
vBCredits v1.4 Copyright ©2007 - 2008, PixelFX Studios
The UNIX and Linux Forums Content Copyright ©1993-2009. All Rights Reserved.Ad Management by RedTyger

Content Relevant URLs by vBSEO 3.2.0