Awk 在不破坏格式化的情况下更改列的内容

Awk 在不破坏格式化的情况下更改列的内容,awk,gawk,Awk,Gawk,$echo“ab”| awk'{print$0;$1=“1”;print$0}' a b 1b 我希望收到如下格式的输出: a b 1 b 有没有简单的方法可以做到这一点(没有IFS、OFS更改)? 我在大桌子上换柱子,然后它看起来很难看。 我不想重新格式化每一列 谢谢。您最好的选择可能是对输出进行后期处理。也许可以简单地说: $ ... | awk ... | column -t $ ... | 啊…|t列 会有用的。(除非“我不想格式化每一列”表示“我不想重新格

$echo“ab”| awk'{print$0;$1=“1”;print$0}' a b 1b

我希望收到如下格式的输出:

 a       b
 1       b
有没有简单的方法可以做到这一点(没有IFS、OFS更改)? 我在大桌子上换柱子,然后它看起来很难看。 我不想重新格式化每一列


谢谢。

您最好的选择可能是对输出进行后期处理。也许可以简单地说:

$ ... | awk ... | column -t $ ... | 啊…|t列
会有用的。(除非“我不想格式化每一列”表示“我不想重新格式化每一行”,例如“我不想后期处理”。在这种情况下,我会问,“为什么不?”)

也许你最好的办法是后期处理输出。也许可以简单地说:

$ ... | awk ... | column -t $ ... | 啊…|t列 会有用的。(除非“我不想格式化每一列”表示“我不想重新格式化每一行”,例如“我不想后期处理”。在这种情况下,我会问“为什么不?”)

一个可能的答案(假设列数固定):

另一个可能的答案(假设你没有很好的理由避免改变OFS,因为,你知道,这就是拥有OFS的全部意义!)

第二种方法的优点是无论文本文件有多少列都可以工作


编辑以添加:

为了解释为什么我认为你对使用OFS的厌恶是奇怪的,只是你得到格式更改的全部原因是因为OFS的原因。输出字段分隔符(OFS)默认为单个空格。当您第一次打印$0时,您没有进行任何修改,因此$0是不变的行。通过更改其中一条记录,您使Awk通过重新组合各个字段中的$0来重新评估该行。当然,重新组装后,Awk在字段之间插入OFS。因为这就是它应该做的。引用相关手册页(手册呆滞):

当引用
$0
时,为现有字段赋值会导致重建整个记录。 类似地,将值分配给
$0
会导致记录重新打印,从而为字段创建新值

现在我同意第一次打印和第二次打印对字段的处理有点不一致,但语言就是这样。OFS不会插入,直到您实际更改字符串,并且它实际计算字段和重建等等


进一步编辑以添加:

看这些:

$ awk 'BEGIN { printf("|%s|\n", OFS) }'
| |
$ awk 'BEGIN { OFS="\t" ; printf("|%s|\n", OFS) }'
|   |
$ 
您的第一个示例中的Awk行为是否变得更加清晰,以及您是否理解了为什么实际需要OFS或printf之类的东西?

一个可能的答案(假设列数固定):

另一个可能的答案(假设你没有很好的理由避免改变OFS,因为,你知道,这就是拥有OFS的全部意义!)

第二种方法的优点是无论文本文件有多少列都可以工作


编辑以添加:

为了解释为什么我认为你对使用OFS的厌恶是奇怪的,只是你得到格式更改的全部原因是因为OFS的原因。输出字段分隔符(OFS)默认为单个空格。当您第一次打印$0时,您没有进行任何修改,因此$0是不变的行。通过更改其中一条记录,您使Awk通过重新组合各个字段中的$0来重新评估该行。当然,重新组装后,Awk在字段之间插入OFS。因为这就是它应该做的。引用相关手册页(手册呆滞):

当引用
$0
时,为现有字段赋值会导致重建整个记录。 类似地,将值分配给
$0
会导致记录重新打印,从而为字段创建新值

现在我同意第一次打印和第二次打印对字段的处理有点不一致,但语言就是这样。OFS不会插入,直到您实际更改字符串,并且它实际计算字段和重建等等


进一步编辑以添加:

看这些:

$ awk 'BEGIN { printf("|%s|\n", OFS) }'
| |
$ awk 'BEGIN { OFS="\t" ; printf("|%s|\n", OFS) }'
|   |
$ 

您的第一个示例中的Awk行为是否变得更加清晰,以及您是否理解了为什么实际需要OFS或printf之类的东西?

您也可以使用替换

$ echo "a       b" | awk '{print $0; gsub("^[^ \t]","1"); print $0}'
a       b
1       b

也可以使用替换

$ echo "a       b" | awk '{print $0; gsub("^[^ \t]","1"); print $0}'
a       b
1       b

谢谢你的回答。这真的让人理解了这个问题。谢谢你的回答。这确实让我理解了这个问题。这是我在开始时做的,但是“| column-t”是更好的方式。我可以更改我想要的任何列,并且在最后仍然有很好的格式化表。这是我在开始时做的,但是“|column-t”是更好的方式。我可以更改任何我想要的列,并且在最后仍然有一个很好的格式化表。