Operator | Usage |
---|---|
&& |
expr1 && expr2
|
|| |
expr1 || expr2
|
! |
! expr
|
awk: not an option: -i
An example is worth one thousand words., so enjoy your reading !
for unit in '' s m; do for duration in 0 1 2 10 100; do value="$duration$unit" echo -n "'$value'." awk ' /^[0-9]+$/ { if($0 < 2) print $0 " second"; else print $0 " seconds"; } /^[0-9]+[ms]$/ { number=strtonum($0) unit=gensub(/^[0-9]+([ms])/, "\\1", "g"); switch (unit) { case /m/: longUnit="minute" break case /s/: longUnit="second" break } if(number > 1) print number" "longUnit"s"; else print number" "longUnit ; } ' <<< "$value" done done | column -s '.' -t
'0' 0 second '1' 1 second '2' 2 seconds '10' 10 seconds '100' 100 seconds '0s' 0 second '1s' 1 second '2s' 2 seconds '10s' 10 seconds '100s' 100 seconds '0m' 0 minute '1m' 1 minute '2m' 2 minutes '10m' 10 minutes '100m' 100 minutes
cat << EOF | awk ' BEGIN { followingWord=""; myVariable=""; } /FOO/ { followingWord=gensub(/.*FOO ([^ ]+).*/, "\\1", "g") } /BAR/ { myVariable="A" } /BAZ/ { myVariable="B" } { if((length(followingWord) > 0) && (length(myVariable) > 0)) { print followingWord" ("length(followingWord)") "myVariable" ("length(myVariable)")." followingWord=""; myVariable=""; } } ' Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut FOO labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex BAR ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore BAZ eu fugiat nulla pariatur. EOF
labore (6) A (1).
[docker-ce-stable] name=Docker CE Stable - $basearch baseurl=https://download.docker.com/linux/centos/$releasever/$basearch/stable enabled=1 gpgcheck=1 gpgkey=https://download.docker.com/linux/centos/gpg [docker-ce-stable-source] name=Docker CE Stable - Sources baseurl=https://download.docker.com/linux/centos/$releasever/source/stable enabled=0 gpgcheck=1 gpgkey=https://download.docker.com/linux/centos/gpgI want to list the IDs of those having
enabled=1
:
curl -s https://download.docker.com/linux/centos/docker-ce.repo | awk ' \ BEGIN { repoId=""; } \ /^ *$/ { repoId=""; } \ /^\[.*\]/ { repoId=$0; } \ /^enabled=1/ { if (repoId != "") { result=gensub(/[\[\]]/, "", "g", repoId); print result; } }'
docker-ce-stable
while read line; do echo -e "\t$line" echo "$line" | awk '{ link=$1; target=""; for(i=2; i<=NF; i++) { if($i!="->") link=link" "$i; else break; } for(j=i+1; j<NF; j++) target=target""$j" "; target=target""$NF; print " LINK: \047"link"\047, TARGET: \047"target"\047"; }' echo done < <(find -type l -exec ls -l {} + | awk '{ for (i=1; i<9; i++) $i=""; print $0; }')Explanations :
print
display single quotes '
(see comments of this answer)#!/usr/bin/env bash value1=120 # initial value : 160 # tested values : 200, 140, 100 # decreasing from the initial value : more bass sounds value2=0.5678 # initial value : 0.87055 # tested values : 0.747, 0.777, 0.789 # increasing values above 3.xxx : extreme bass sounds (?), hardly audible # around 0.5xxxxx : nice chime sounds value3=13 # initial value : 10 # tested values : 13, 17, 26 # increasing values : more high-pitched sounds # 26 makes some 'D2-R2' blips value4=128 # no effect so far :-( # initial value : 128 awk "function wl() { rate=64000; return (rate/$value1)*($value2^(int(rand()*$value3)))}; BEGIN { srand(); wla=wl(); while(1) { wlb=wla; wla=wl(); if (wla==wlb) {wla*=2;}; d=(rand()*10+5)*rate/4; a=b=0; c=$value4; ca=40/wla; cb=20/wlb; de=rate/10; di=0; for (i=0;i<d;i++) { a++; b++; di++; c+=ca+cb; if (a>wla) {a=0; ca*=-1}; if (b>wlb) {b=0; cb*=-1}; if (di>de) {di=0; ca*=0.9; cb*=0.9}; printf(\"%c\",c)}; c=int(c); while(c!=$value4) { c<$value4?c++:c--; printf(\"%c\",c)};};}" | aplay -r 64000
BEGIN
rule is executed once only, before the first input record is read (example)BEGINFILE
END
rule is executed once only, after all the input is read (example)ENDFILE
rule :
END
rules23a5b5a3d9ba0d2c6277dbdaf2557033 /etc/alternatives/awk 23a5b5a3d9ba0d2c6277dbdaf2557033 /usr/bin/gawk
Once gawk is installed, it can be invoked with awk.
$0
being the whole line itself) :3 4
c averell
line 1: a line 2: b line 3: c line 4: d line 5: e
\n
(NEWLINE
) : by default Awk considers 1 record == 1 line of input~ is the Awk operator to match a regular expression.
logFile='/var/log/lighttpd/www.example.com.log'; resultFile='./result.csv'; tmpFile=$(mktemp --tmpdir tmp.result.XXXXXXXX); grep '" 500 ' $logFile | sed -r 's/^.*GET ([^ ]*).*HTTP\/1\.." ([0-9]*).*$/\1;\2;/' > $tmpFile; cat $tmpFile | sort | uniq -c | sort -nr > $resultFile; rm $tmpFile
Using grep 1st because sed can't find a match on every line, as we're reporting only on HTTP 500 errors.
Awk is a programmable text filter. Its input can be :
{ print $0 }
, albeit correct, is redundant .An Awk script is made of 3 blocks :
Awk reads the input line by line, then applies the specified filter(s) to detect whether or not to process the current line. Before starting processing a line, Awk splits it into fields and stores fields values in $1
(1st field), $2
, ..., $NF
(last field). $0
is the whole input line. The fields separator (specified with FS) defaults either to [SPACE] or [TAB] (details).
There is no need to use grep together with Awk as Awk "RegExp matches" lines to process.
Criteria | select matching lines | select not matching lines |
---|---|---|
line number within input |
awk 'NR==n {doSomething}' c |
a b d |
line vs regular expression |
awk '/regEx/ {doSomething}'
|
awk '!/regEx/ {doSomething}'echo -e 'foo\nbar\nbaz' | awk '!/a/ {print $0}' foo(source, example) |
line vs number of fields |
echo -e 'field1\nfield1\tfield2\nfield1\tfield2\tfield3' | awk 'NF == 2 {print $0}'
field1 field2 |
|
field vs number |
echo -e 'foo\t12\nbar\t34\nbaz\t56' | awk '$2 > 25 {print $0}'
bar 34 baz 56 Awk is smart enough to strip leading zeroes :
Trying to filter data based on line numbers returned by grep -n with a construct like :may fail because of the returned color codes.
|
|
field vs string |
awk '$n == "value" {doSomething}'for i in {1..3}; do echo "foo$i bar$i baz$i"; done | awk '$2 == "bar2" {print $0}' foo2 bar2 baz2 |
awk '$n != "value" {doSomething}'for i in {1..3}; do echo "foo$i bar$i baz$i"; done | awk '$2 != "bar2" {print $0}' foo1 bar1 baz1 foo3 bar3 baz3 |
field vs regular expression |
awk '$n ~ /regEx/ {doSomething}' |
awk '$n !~ /regEx/ {doSomething}'for i in {1..3}; do echo "foo$i bar$i baz$i"; done | awk '$2 !~ /a.1/ {print $0}' foo2 bar2 baz2 foo3 bar3 baz3 |
field vs regular expression with if / else construct (source) |
for i in {1..3}; do echo "foo$i bar$i baz$i"; done | awk '{ if($2 ~ "a.2") {print "MATCH : "$2 } else {print "NO MATCH"} }'
NO MATCH MATCH : bar2 NO MATCH |
|
several conditions |
awk 'condition1 logicalOperator condition2 logicalOperator ... conditionN {doSomething}'logicalOperator can be (source) :
|
If the numerical value has a unit letter, it doesn't work anymore :
foo 8U ooops !
bar 34U
baz 56U
solution :
bar 34U baz 56U
Try it :
%
/, "", $5)} {if(strtonum($5) > 50) {print $0}}'
awk 'BEGIN { print "trailing unit (single letter) : " strtonum("123U") print "trailing unit (word) : " strtonum("123potatoes") print "leading unit (single letter) : " strtonum("Y123") print "leading unit (word) : " strtonum("banana123") }'
trailing unit (single letter) : 123 OK trailing unit (word) : 123 OK leading unit (single letter) : 0 KO leading unit (word) : 0 KO
Flag | Usage |
---|---|
-F x | use x as the input Field separator |
-i awkLibrary --include awkLibrary |
load the specified library awkLibrary (example) |
-v variable=value |
|
Exit status | Description |
---|---|
0 aka UNIX_SUCCESS |
No problem during execution, including when no match was found. Check it : a 0 0 |
1 aka UNIX_FAILURE |
An error occurred |
2 |
Fatal error |
printf adds no carriage return after printing. print does.
Then count occurrences :[13-Nov-2013 03:03:35 Europe/Paris] PHP Warning: Memcached::touch(): ... in ....php on line 45 [13-Nov-2013 03:04:42 Europe/Paris] PHP Warning: file_get_contents(http://...): HTTP/1.0 404 Not Found in ...php on line 202 ...let's say you'd like to remove the date/time field to group and count similar errors. To do so :
awk '{ for (i=1;i<=3;i++) $i="";print }' file.log | awk '{sub(/^[ \t]+/, ""); print}' | sort | uniq -c | sort -nr
//
operator to select the matching line :
/stuffToMatch/
'(nothing)
$0 ~ /stuffToMatch/
'(nothing)no match found, as said above
stuffToMatch
'fruit: apple fruit: banana vegetable: carrotmatches everything
$0 ~ stuffToMatch
'fruit: banana vegetable: carrot
$1 ~ stuffToMatch
'vegetable: carrot
$2 ~ stuffToMatch
'fruit: bananaAll examples work as expected
"a"
1a 3a
a
1a 2b 3a 4b
1a 2b 3a 4b
1a 3a
if input =~ "foo.=A"
continue
else
print input
$0 ~ "("value"|B)C"
'AC BC
echo -e 'A\tB\tC\tD\nE\tF\tG\tH\n\nI\tJ\tK\tL' | awk '!/^$/ {print $3}'
C G K
value1 value2
/key1|key2/
part of the awk command is a "normal" regular expression alternationprintf $2 " "
part simply prints the 2nd field of each matching line, followed by a space