我想运行一个 for 循环,它计算以下任务:运行awk
10 次,求和输出并打印最终结果。代码附在下面:
sum=0
for i in {1..10}
do
count=`awk '{if ($NF==$i) {print $NF}}' * | wc -l`
sum=$[sum+count]
echo $sum
done
问题是,如果我更改$NF==$i
为$NF==1
,那么结果是正确的,但我想使用 for 循环运行 10 次。
代码中存在什么问题?
答案1
在以下位置完成整个事情会更有效awk
:
awk -v n=0 '
{for (i = 1; i <= 10; i++) if ($NF == i) {n++; break}}
END {print n}' ./*
或者如果最后一个字段始终是整数:
awk -v n=0 '
$NF >= 1 && $NF <= 10 {n++}
END {print n}' ./*
或者,如果您希望比较是词法的,并且只允许这些数字的1
, 2
, 3
...,10
表示(而不是01
, 1e0
, 1.0
...):
awk -v n=0 '
$NF ~ /^([123456789]|10)$/ {n++}
END {print n}' ./*
答案2
这里的问题是您试图在单引号内进行 shell 变量扩展' ... '
。但是,在单引号内,壳变量扩展被暂停(参见例如这个答案这里或Lhunath 和 GreyCat 的 Bash 指南),这就是为什么实际上建议这样做的原因:因为$
在取消引用各个输入字段时执行类似的功能awk
(但字段编号也可以由变量名表示,如在例如中$NF
),将程序封装在单个输入字段中引号避免了并发的“变量扩展”。
awk
在您的情况下,您可以使用以下命令将值“导入”到程序中
awk -v fieldnr="$i" '{if ($NF==fieldnr) {print $NF}}'
尽管如此,您的问题似乎可以在 中完全解决awk
,所以也许您想更详细地解释您想要完成的任务,我们可以尝试找到一种更优雅(并且可能更快)的方法;不过,提出另一个问题可能是合理的......
答案3
如果您的脚本按照我的想法执行(即sum
从 1 循环到 10 时打印匹配行的增量值),那么您真正需要生成 shell 脚本将生成的输出的是:
awk '
{ counts[$NF]++ }
END {
for (i=1; i<=10; i++) {
sum += counts[i]
print sum
}
}
' *
上面的内容未经测试,因为您没有提供任何示例输入/输出来进行测试。
答案4
#!/bin/bash
# Tested with -- GNU bash, version 4.4.20(1)-release (x86_64-pc-linux-gnu)
set -e
for i in `seq 1 1000`
do
echo $i
# Run your command here
done