在下面的代码片段中,$2
awk 返回空。我究竟做错了什么?我正在尝试找出 MAX 和 MIN 之间的差异。
#!/bin/ksh
if [ $# -ne 1 ]; then
echo "Usage: sh `basename ${0}` filename";
exit 1;
fi
if [ ! -s ${1} ]; then
echo "file doesn't exist or is empty";
exit 1;
fi
sed -e '/^$/d' -e '/^#/d' ${1} |
awk -F'=' '
BEGIN {
MIN=$2; MAX=$2; print MIN;
}
{
if ( $2 > MAX )
{
MAX = $2;
}
else if ( $2 < MIN )
{
MIN = $2;
}
}
END {
DIFF=MAX-MIN; print "DIFF:" DIFF;
}
'
然而,这工作正常。为什么$2
在该部分不起作用BEGIN
?
#!/bin/ksh
if [ $# -ne 1 ]; then
echo "Usage: sh `basename ${0}` filename";
exit 1;
fi
if [ ! -s ${1} ]; then
echo "file doesn't exist or is empty";
exit 1;
fi
sed -e '/^$/d' -e '/^#/d' ${1} |
awk -F'=' '
{
if ( MAX == "" || MIN == "" )
{
MAX = MIN = $2;
}
else
{
if ( $2 > MAX )
{
MAX = $2;
}
else if ( $2 < MIN )
{
MIN = $2;
}
}
}
END {
DIFF=MAX-MIN; print "DIFF:" DIFF;
}
'
答案1
BEGIN
模式被执行前读取任何输入,因此不会在任何块中定义任何引用输入的变量,例如NR
、字段等。你的第二种方法是正确的,而且更好。$0
BEGIN
POSIX awk 规范(强调矿):
awk 实用程序应识别两种特殊模式:BEGIN 和 END。每个 BEGIN 模式应匹配一次并执行其关联的操作在读取输入的第一条记录之前...
1 顺便说一句,它也很好,因为它不会假设最小值或最大值受特定值(如 0)限制,这是人们在互联网上找到的许多单行假设的假设。
答案2
如果你想在输入文本的第一行执行命令,你应该使用NR==1
pattern,而不是BEGIN
.
awk -F'=' '
NR==1 {
MIN=$2; MAX=$2; print MIN;
}
NR>1 {
if ( $2 > MAX )
{
MAX = $2;
}
...
正如@jw013所述,BEGIN
模式是在阅读第一行之前执行的操作。