2009-09-16 5 views
8

Chcę napisać ogólny skrypt awk, który może pobrać jako dane wejściowe plik i numer pola (w tym pliku) i podać średnią wartość tego pola w ten plik. Chciałbym używać go coś takiego:Ogólny skrypt awk do obliczania średniej na dowolnym polu za pomocą argumentu wiersza poleceń

bash$ avg.awk 3 input.file 
22 
bash$ avg.awk 4 input.file 
2001 

Oczywiście, można napisać skrypt jeśli wiem, które pole (na przykład 3 $) idę do średniej wcześniej. To byłoby coś takiego:

//{tot+=$3; count++} 
END{ 
    print tot/count; 
} 

Ale chcę mieć możliwość zmiany pola, które chcę uśrednić za pomocą opcji wiersza poleceń. Czy to jest możliwe? Dzięki!

Odpowiedz

11

Ten będzie robić to, co chcesz:

$ cat avg.awk 
#!/usr/bin/env awk -f 
# Calculate average, syntax: avg.awk field-number file 
BEGIN { field = ARGV[1]; ARGV[1] = "" } 
{ sum += $field } 
END { print sum/NR } 

$ cat data 
1 5 7 
3 6 5 
8 4 6 

$ avg.awk 1 data 
4 

$ avg.awk 2 data 
5 

$ avg.awk 3 data 
6 
+1

Nie mogłem używać env tak, jak opisałeś. Na razie właśnie postawiłem prawdziwą ścieżkę do awk. Działa to jednak. Dzięki! – Ritesh

+0

Używanie/usr/bin/env jest moim sposobem radzenia sobie z faktem, że różne systemy instalują awk w różnych miejscach. Możesz chcieć wydać polecenie "który env" z wiersza poleceń, aby dowiedzieć się, gdzie w twoim systemie znajduje się env. –

+0

/usr/bin/env: awk -f: Brak takiego pliku lub katalogu To jest wiadomość, którą otrzymuję. env znajduje się w/usr/bin/env. Chociaż rozwiązałeś mój początkowy problem, chciałbym się dowiedzieć, w jaki sposób można użyć env. – Ritesh

5
{ tot += $field; count++ } 
END { print tot/count } 

wywołanie jak awk -v field=3 -f avg.awk input.file

+2

Można użyć NR aby uniknąć zmienną ilość: {tot + = $ F} END {print tot/NR} –

+1

... zakładając, że OP nie chce odfiltrowywać nagłówków lub pominąć rekordów. :) –

+0

Dzięki, to na pewno działa! Druga odpowiedź sprawia, że ​​linia poleceń jest łatwiejsza w użyciu :) – Ritesh

Powiązane problemy