macos – 在awk字段分隔符更改后重新评估记录中的字段
(这是我在这里发表的第一篇文章,如果我以错误的方式提问,请原谅我.)
我在OSX Maverick上学习awk.我在awk上经历了this tutorial. 我试图在该教程中重现与awk_example4a.awk类似的内容. 所以我想出了这个awk程序/脚本/参数(不知道你叫什么?): BEGIN { i=1 } { print "Line " i; print "$1 is " $1,"n$2 is " $2,"n$3 is " $3; FS=":"; $0=$0; print "With the new FS - line " i; print "$1 is " $1,"n$3 is " $3; FS=" "; i++; } 输入文件如下所示: A1 B1:B2 C2 A1:A2 B2:B3 C3 我想要做的是先用默认的FS(空格)处理每一行/记录,然后用新的FS(“:”)重新处理它,然后在转到下一条记录之前恢复默认的FS . 根据教程,$0 = $0应该使用新的字段分隔符来重新评估字段,因此据说给我一个如下所示的输出: Line 1 $1 is A1 $2 is B1:B2 $3 is C2 With the new FS - line 1 $1 is A1 B1 $2 is B2 C2 $3 is Line 2 $1 is A1:A2 $2 is B2:B3 $3 is C3 With the new FS - line 2 $1 is A1 $2 is A2 B2 $3 is B3 C3 但相反,我得到: Line 1 $1 is A1 $2 is B1:B2 $3 is C2 With the new FS - the line 1 $1 is A1 $2 is B1:B2 $3 is C2 Line 2 $1 is A1:A2 $2 is B2:B3 $3 is C3 With the new FS - the line 2 $1 is A1:A2 $2 is B2:B3 $3 is C3 即FS更改后,字段尚未重新评估. 因此,如果$0 = $0不起作用(也不做$1 = $1; $2 = $2),我如何使用不同的FS重新评估同一行? 谢谢. 解决方法
TL; DR:
FreeBSD / OS X awk在当前记录处理完成之前不会对FS(字段分隔符)应用更改 – 这种行为实际上是POSIX强制的(见下文). 解决方法:不要更改FS并使用函数split()代替: { print "Line " ++i print "$1 is " $1 "n$2 is " $2 "n$3 is " $3 split($0,flds,":") # split current line by ':' into array `flds` print "With the new FS - line " i print "field1 is " flds[1] "nfield2 is " flds[2] "nfield3 is " flds[3] } >注意如何在数值上下文中依赖未初始化的变量默认为0来消除BEGIN块. 请继续阅读,了解有趣的多平台兼容性详细信息. POSIX spec. for Before the first reference to a field in the record is evaluated,the record shall be split into fields,according to the rules in Regular Expressions,**using the value of FS that was current at the time the record was read**. 关于将新值分配给$0或特定字段,相同的源指出: The symbol $0 shall refer to the entire record; setting any other field causes the re-evaluation of $0. Assigning to $0 shall reset the values of all other fields and the NF built-in variable. 换句话说:假设重新赋值情况没有另外说明,则只能引用POSIX规范中给定FS值的范围.要求它对于给定的输入记录是恒定的. 因此,FreeBSD / OS X awk是模型公民,而GNU awk和mawk通过不按规则播放并将FS更改应用于重新分配到$0或任何特定字段的当前记录来提供更大的灵活性. 但请注意,GNU awk(自v4.1.1起)甚至不会使用–posix选项更改该行为,该选项的明确意图是导致符合POSIX的行为.如果我正在阅读POSIX规范.正确(告诉我我是否),这应该被视为一个错误. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |