(这是我在这里的第一篇文章,所以如果我问错了问题,请原谅我。)
我正在awk我的 OSX Maverick 上学习。我正在awk 上浏览本教程。
我正在尝试在该教程中重现类似于 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$2 is " $2, "\n$3 is " $3;
FS=" ";
i++;
}
Run Code Online (Sandbox Code Playgroud)
输入文件如下所示:
A1 B1:B2 C2
A1:A2 B2:B3 C3
Run Code Online (Sandbox Code Playgroud)
我想要做的是首先使用默认值FS(空格)处理每一行/记录,然后使用新的FS(“:”)重新处理相同的行/记录,然后FS在转到下一条记录之前恢复默认值。
根据教程,$0=$0应该awk使用新的字段分隔符重新评估字段,因此应该给我一个看起来像这样的输出:
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
Run Code Online (Sandbox Code Playgroud)
但相反,我得到:
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
Run Code Online (Sandbox Code Playgroud)
即字段FS在更改后没有被重新评估。
因此,如果$0=$0不起作用(并且也不起作用$1=$1; $2=$2),我如何让 awk 使用不同的 重新评估同一行FS?
谢谢你。
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]
}
Run Code Online (Sandbox Code Playgroud)
BEGIN通过依赖0数字上下文中默认的未初始化变量来消除该块。,实例已从print语句中删除,因为每个实例都会插入一个空格(输出字段分隔符的默认值OFS),在本例中不需要。;因此不需要终止它们。请继续阅读有趣的多平台兼容性详细信息。
POSIX规范。对于awk各州(强调我的):
在评估对记录中字段的第一次引用之前,该记录应 根据正则表达式中的规则拆分为字段, **使用读取记录时当前的 FS 值**。
关于为$0特定字段分配新值,同一来源指出:
符号 $0 指的是整个记录;设置任何其他字段原因 重新评估为0美元。分配给 $0 将重置所有其他的值 字段和 NF 内置变量。
换句话说:鉴于重新分配情况没有另外说明,这是对FSPOSIX 规范中给定值范围的唯一引用。要求它对于给定的输入记录是恒定的。
肯定存在歧义,如果规范肯定会有所帮助。解决了这个问题 - 也就是说,保守且因此更安全的解释是假设处理给定记录时恒定 FS。
因此,FreeBSD/OS X 是awk模型公民,而GNUawk也mawk提供了更大的灵活性,不遵守规则,甚至在重新分配到或任何特定字段时对当前FS记录应用更改$0。
但请注意,GNU awk(从 v4.1.1 开始)甚至不会使用该--posix选项更改该行为,该选项的明确意图是导致符合 POSIX 的行为。如果我正在阅读 POSIX 规范。正确地(请告诉我是否是),这应该被视为一个错误。
| 归档时间: |
|
| 查看次数: |
774 次 |
| 最近记录: |