我试图简单地打印列$4
,然后$NF
打印以下数据:
000 0 00 NUL '\0' (null character) 100 64 40 @
001 1 01 SOH (start of heading) 101 65 41 A
002 2 02 STX (start of text) 102 66 42 B
003 3 03 ETX (end of text) 103 67 43 C
004 4 04 EOT (end of transmission) 104 68 44 D
005 5 05 ENQ (enquiry) 105 69 45 E
006 6 06 ACK (acknowledge) 106 70 46 F
007 7 07 BEL '\a' (bell) 107 71 47 G
010 8 08 BS '\b' (backspace) 110 72 48 H
这样我就得到:
NUL
SOH
STX
ETX
EOT
ENQ
ACK
BEL
BS
@
A
B
C
D
E
F
G
H
其中awk
等待第一个操作完成然后执行下一列的打印输出。
我试过:
awk '{print $4} {print $NF}'
但这显然只是一个接一个地打印它们并将它们全部混合在一起。
我正在努力更好地理解awk
并搞乱,请耐心等待。
答案1
AFAIK,您需要存储这些$NF
值并将它们打印在一个END
块中
awk '{a[NR] = $NF; print $4} END{for(i=1;i<=NR;i++) print a[i]}' file
或对文件进行两次遍历
awk 'NR==FNR {print $4; next} {print $NF}' file file
答案2
@steeldriver 已经展示了如何完全在 awk 中完成此操作,虽然这超出了您对这个特定问题的需要,但还请考虑极其有用的装饰-排序-取消装饰习惯用法对于这样的问题:
$ awk -v OFS='\t' '{print 1, NR, $4 ORS 2, NR, $NF}' file | sort -nk1,2 | cut -f3-
NUL
SOH
STX
ETX
EOT
ENQ
ACK
BEL
BS
@
A
B
C
D
E
F
G
H
您可以在 GNU awk 中实现完全类似的东西(对于数组的数组 和sorted_in
),如下所示:
$ awk '
{ a[1][NR]=$4; a[2][NR]=$NF }
END {
PROCINFO["sorted_in"] = "@ind_num_asc"
for (i in a) for (j in a[i]) print a[i][j]
}
' file
NUL
SOH
STX
ETX
EOT
ENQ
ACK
BEL
BS
@
A
B
C
D
E
F
G
H
答案3
使用awk
:
$ awk '{print $4; a = ((a) ? a ORS : "") $NF} END{print a}' file
@EdMorton 建议的一种更简单、更有效的方法是
$ awk '{print $4; a=a $NF ORS} END{printf "%s", a}' file
使用awk
和datamash
:
$ awk '{print $4, $NF}' file | datamash -W --output-delimiter $'\n' transpose
以下命令的输出如下:
$ awk '{print $4, $NF}' ex | datamash -W transpose
NUL SOH STX ETX EOT ENQ ACK BEL BS
@ A B C D E F G H
在此输出值由 分隔tab
,可以通过设置更改--output-delimiter
到\n
。
$ awk '{print $4, $NF}' ex | datamash -W --output-delimiter $'\n' transpose
NUL
SOH
STX
ETX
EOT
ENQ
ACK
BEL
BS
@
A
B
C
D
E
F
G
H