如何将bash参数传递给awk脚本?

4

我有一个awk文件:

#!/bin/awk -f
BEGIN {

}
{
        filetime[$'$colnumber']++;
}
END {
        for (i in filetime) {
                print filetime[i],i;
        }
}

并且 bash 脚本:

#!/bin/bash
var1=$1
awk -f myawk.awk

当我运行时:

ls -la | ./countPar.sh 5

我收到了错误信息:

ls -la | ./countPar.sh 5
awk: myawk.awk:6:         filetime[$'$colnumber']++;
awk: myawk.awk:6:                   ^ invalid char ''' in expression

为什么要用$colnumber替换成5,这样awk就能读取ls输出的第5列。谢谢。

1
这似乎是对这个问题的后续:http://stackoverflow.com/q/8551780/226201。正如其他人所指出的,Bash环境和Awk环境是分离的,如果你想从一个环境传递参数到另一个环境,必须显式地进行。 - Samus_
3个回答

5
你可以直接从命令行向awk脚本传递变量。
更改以下这一行:
filetime[$'$colnumber']++;

To:

filetime[colnumber]++;

并运行:

ls -al | awk -f ./myawk.awk -v colnumber=5

如果你真的想使用一个bash包装器:

#!/bin/bash
var1=$1
awk -f myawk.awk colnumber=$var1

如果您想使用环境变量,请使用以下命令:

(在您的脚本中进行与上面相同的更改。)

#!/bin/bash
export var1=$1
awk -f myawk.awk

并且:

filetime[ENVIRON["var1"]]++;

我真的不明白你的awk脚本的目的是什么。最后一部分可以简化为:

END { print filetime[colnumber],colnumber; }

通常解析ls的输出并不是一个好主意。


意思是结合bash和awk。我只是举了一个例子来说明输入参数,bash脚本更加复杂。 - user710818
3
我不确定我理解你的意思,所以添加了更多选项。你不能在awk脚本中直接使用普通的shell替换,因为那样不起作用——shell只会对其参数进行替换,而不是在命令行上指定的任意文件中进行替换(在一般情况下,它甚至不会检查哪些是文件,哪些不是)。 - Mat
有趣的是,我不知道你可以在awk中传递变量而不使用-v。 - eugenevd
@twqqis:请参见此处的例子,有/没有使用-v选项时的行为略有不同。 - Mat

2
最简单的方法是:
#!/bin/bash
var=$1
awk -v colnumber="${var}" -f /your/script

但是在您的awk脚本中,您不需要在colnumber前面加上$

希望对您有所帮助。


0

将3个变量传递给脚本myscript.sh var1是设置条件的列号。 而var2和var3则是输入文件和临时文件。

#!/bin/ksh
var1=$1
var2=$2
var3=$3
awk -v col="${var1}" -f awkscript.awk ${var2} > $var3
mv ${var3} ${var2}

执行方式如下 -

./myscript.sh 2 file.txt temp.txt

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接