There are many common functions (especially arithmetic/mathematics) that are not built into awk
that I need to write myself all the time.
For example:
c=min(a,b)
, so in awk
i constantly write c=a<b?a:b
c=max(a,b)
c=abs(a)
so i have to constantly write c=a>0?a:-a
Ideally, I could write these functions into an awk
source file, and "include" it into all of my instances of awk, so I can call them at will.
I looked into the "@include" functionality of GNU's gawk
, but it just executes whatever is in the included script - i.e. I cannot call functions.
I was hoping to write some functions in e.g. mylib.awk
, and then "include" this whenever I call awk
.
I tried the -f mylib.awk
option to awk
, but the script is executed - the functions therein are not callable.
Running Long Programs In order to tell awk to use that file for its program, you type: awk -f source-file input-file1 input-file2 … The -f instructs the awk utility to get the awk program from the file source-file (see Command-Line Options). Any filename can be used for source-file .
Awk is mostly used for pattern scanning and processing. It searches one or more files to see if they contain lines that matches with the specified patterns and then perform the associated actions. Awk is abbreviated from the names of the developers – Aho, Weinberger, and Kernighan.
GNU AWK may be the most widely deployed version because it is included with GNU-based Linux packages.
With GNU awk:
$ ls lib
prims.awk
$ cat lib/prims.awk
function abs(num) { return (num > 0 ? num : -num) }
function max(a,b) { return (a > b ? a : b) }
function min(a,b) { return (a < b ? a : b) }
$ export AWKPATH="$PWD/lib"
$ awk -i prims.awk 'BEGIN{print min(4,7), abs(-3)}'
4 3
$ cat tst.awk
@include "prims.awk"
BEGIN { print min(4,7), abs(-3) }
$ awk -f tst.awk
4 3
You can have multiple -f program-file
options, so one can be your common functions and the other can be a specific problem solving awk script, which will have access to those functions.
awk -f common-funcs.awk -f specific.awk file-to-process.txt
I don't know if this is what you were looking for, but it's the best I've come up with. Here's an example:
$ cat common_func.awk
# Remove spaces from front and back of string
function trim(s) {
gsub(/^[ \t]+/, "", s);
gsub(/[ \t]+$/, "", s);
return s;
}
$ cat specific.awk
{ print $1, $2 }
{ print trim($1), trim($2) }
$ cat file-to-process.txt
abc | def |
2$ awk -F\| -f common_func.awk -f specific.awk file-to-process.txt
abc def
abc def
With regular awk (non-gnu) you can't mix the -f program-file
option with an inline program. That is, the following won't work:
awk -f common_func.awk '{ print trim($1) }' file-to-process.txt # WRONG
As pointed out in the comments, however, with gawk you can use the -f
option together with -e
:
awk -f file.awk -e '{stuff}' file.txt
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With