怎样`... | awk '$1=$1'` 删除多余的空格?

怎样`... | awk '$1=$1'` 删除多余的空格?

以我的理解,$1是第一个字段。但奇怪的是,awk '$1=$1'省略了额外的空格。

$ echo "$string"
foo    foo bar               bar

$ echo "$string" | awk '$1=$1'
foo foo bar bar

为什么会发生这种情况?

答案1

当我们为字段变量赋值时,即。的值$1被分配给 field $1,awk 实际上$0通过将它们与默认字段分隔符(或OFS)空间连接来重建它。

我们也可以在以下场景中得到相同的情况......

echo -e "foo foo\tbar\t\tbar" | awk '$1=$1'
foo foo bar bar

echo -e "foo foo\tbar\t\tbar" | awk -v OFS=',' '$1=$1'
foo,foo,bar,bar

echo -e "foo foo\tbar\t\tbar" | awk '$3=1'
foo foo 1 bar

对于 GNU AWK,此行为记录在此处:
https://www.gnu.org/software/gawk/manual/html_node/Changing-Fields.html

$1 = $1 # 强制重建记录

答案2

echo "$string" | awk '$1=$1'

导致 AWK 评估$1=$1,这会将字段分配给自身,并具有重新评估 的副作用$0;然后 AWK 考虑表达式的值,并且因为它非零且非空,所以它执行默认操作,即 print $0

当 AWK 重新计算时,多余的空格将被删除$0:它通过使用分隔符连接所有字段来实现这一点OFS,默认情况下这是一个空格。当 AWK 解析记录时,$0按原样包含整个记录,并$1包含$NF字段(不带分隔符);当任何字段被分配给时,$0从字段值重建。

本例中 AWK 是否输出任何内容取决于输入:

echo "0      0" | awk '$1=$1'

不会输出任何东西。$1=$1计算第一个字段中的任何内容,即0本例中的内容;这是 AWK 中的“假”结果,因此什么也没有发生,也没有任何输出。为了避免这种情况,请转入$1=$1一个操作并让 AWK 在所有情况下打印当前记录:

| awk '{$1=$1}1'

1导致 AWK 始终运行默认操作。

相关内容