AWK - execute string as command?

Tag: awk Author: y308476882 Date: 2012-11-20

This command prints:

$ echo "123456789" | awk '{ print substr ($1,1,4) }'
1234

Is it possible to execute a string as command? For example, this command:

echo "123456789" | awk '{a="substr"; print a ($1,1,4) }'

Result:

$ echo "123456789" | awk '{a="substr"; print a ($1,1,4) }'
awk: {a="substr"; print a ($1,1,4) }
awk:                               ^ syntax error

EDIT:

$ cat tst.awk 
function my_substr(x,y,z) { return substr(x,y,z) }

{ a="my_substr"; print @a($1,1,4) }
[email protected]:~/Pulpit$ echo "123456789" | gawk -f tst.awk
gawk: tst.awk:3: { a="my_substr"; print @a($1,1,4) }
gawk: tst.awk:3:                        ^ nieprawid?owy znak '@' w wyra?eniu
[email protected]:~/Pulpit$ 
But Why do you need it?
I asked with curiosity
Its a pretty common thing to want to define a generic function to, say, iterate over all the elements of an array and perform some operation X on each element where X varies by invocation and being able to assign a function name to X lets you avoid writing a series of "if"s or a switch statement (gawk).

Best Answer

You can call user-defined functions via variables in GNU awk using indirect function calls, see http://www.gnu.org/software/gawk/manual/gawk.html#Indirect-Calls

$ cat tst.awk
function foo() { print "foo() called" }
function bar() { print "bar() called" }

BEGIN {
   the_func = "foo"
   @the_func()

   the_func = "bar"
   @the_func()
}
$ gawk -f tst.awk
foo() called
bar() called

Unfortunately due to internal implementation issues, if you want to call builtin functions that way then you need to write a wrapper for each:

$ cat tst.awk
function my_substr(x,y,z) { return substr(x,y,z) }

{ a="my_substr"; print @a($1,1,4) }
$ echo "123456789" | gawk -f tst.awk
1234

comments:

Do you know of anything similar for POSIX awk?
No, there's nothing like it for POSIX awk.
@Ed Morton, The last example does not work. You can check it again? Thank you.
No need to check it again as I copy/pasted the command working the first time. If you tell us in what way it "does not work" for you, maybe we can help.
@Ed Morton, Look at my edit.

Other Answer1

I don't think it is possible to do that in awk directly, but you can get a similar effect by using the shell. Recall that the awk program is given as a string, and strings are concatenated in the shell just by writing them next to one another. Thus, you can do this:

a=substr
echo "123456789" | awk '{ print '"$a"'($1, 1, 4) }'

resulting in 1234.

comments:

Thank you for a good answer.