我想使用 AWK 解决以下问题。
如果使用 sed 或 Perl 等语言可以实现任何其他解决方案,我们也将不胜感激。
以下是输入:
U,N,UNIX,000,A,5
N,P,SHELL,111,B,6
I,M,UNIX,222,C,7
X,Y,BASH,333,D,8
P,R,SCRIPT,444,E,9
我想要的输出如下:
U,N,,,A,5
N,P,,,B,6
I,M,,,C,7
X,Y,,,D,8
P,R,,,E,9
另请注意:我不知道每行的字段总数。我只知道字段3和4要留空。
答案1
要按比例空白命令中从第 n 个到第 m 个的所有字段awk
,您不应该对这些值进行硬编码;你应该使用“for”循环:
awk 'BEGIN { FS = ","; OFS = ","} {for (i = 3; i <= 4; i++) { $i = "" }; print}' inputfile
如果您想清空不同的范围,请调整上述代码中的值“3”和“4”。
解释:
BEGIN { ... }
在查看文件的任何行之前先处理该块。
OFS
设置输出字段分隔符,并FS
设置输入字段分隔符。我们希望它们都是逗号。
循环for
就像 C 语法一样。在这种情况下,它对as 3 和 as 4执行以下操作{ code block }
。i
值得$i
一提的是,它与 shell 语法完全不同。在 shell 脚本中,变量名必须以 为前缀才能$
扩展为变量的值。在awk
.在 中awk
,i
本身扩展为它的值(在本例中为 3 或 4),并且$
后面跟着一个数字表示场地在那个编号的位置。因此将第 th 字段$i = ""
设置i
为空字符串。
然后print
,不带参数的命令默认打印整行。实际上,它获取由 分隔的行中的所有字段以及由任何先前命令修改的行,并将它们全部打印出来,并在末尾用换行符FS
分隔并后跟换行符。OFS
等效的较短命令:
我觉得如果您要将上面的命令包含在脚本中,它是最干净且最容易扩展的。它非常明确地说明了它正在做什么并且非常可读。另外,整个事情可以分解为一个独立的awk
脚本而无需更改;使用-v
并-F
切换到您的调用时无法自动完成的事情awk
。 (当然,这并不是不使用它们的理由。只是需要注意一些事情。)
特别是对于一次性使用,我将使用以下内容:
awk -F, -v OFS=, '{for (i = 3; i <= 4; i++) { $i = "" }; print}' inputfile
开关-F
设置 的值FS
。该开关允许您在命令行上-v
设置变量的值。awk
更一般地说,该开关对于将 shell 变量作为 awk 变量传递:以及更改使用命令行选项从脚本文件中提取的独立脚本的运行时-v
行为非常有用。-v myawkvar="$myshellvar"
awk
-f scriptname
答案2
</path/to/in_file awk -v 'FS=,' -v 'OFS=,' '{$3=$4=""; print}'
解释
</path/to/in_file
:读取文件到标准中。-v 'FS=,' -v 'OFS=,'
:将文件分隔符和输出文件分隔符设置为,
.'{$3=$4=""; print}'
:将第三个和第四个字段设置为空白,然后打印整行(缩写形式由杰森·瑞恩)。
答案3
sed 's/\([^,]*,\)\{2\}/,,/2' <in >out
U,N,,,A,5
N,P,,,B,6
I,M,,,C,7
X,Y,,,D,8
P,R,,,E,9
这会将第二次出现的一组两个连续的逗号分隔字段替换为两个逗号。
你也可以这样做:
sed 's/[^,]*//4;s///3' <in >out
...它将任何 num 个非逗号字符序列的第四次和第三次出现替换为空。
像 @Wildcard 那样做 - 使用可扩展的循环:
sed -e:t -e'/\n\{2\}/!s/\(\n*\)[^,]*./\n\1/3;/\n$/!tt' -e's///;y/\n/,/'
...或者...
sed -e:t -e's/\n$//;s/\n/&/2;to' \
-e's/\(\n*\)[^,]*./\1\n/3;tt' \
-e:o -ey/\\n/,/
...在哪里3
是您要开始消隐的字段编号,,
是分隔符,并且2
是您要全部空白的字段数。
不管你怎么写...
sed "$script" <<""
U
N,P
I,M,UNIX
X,Y,BASH,333
P,R,SCRIPT,444,E,9
U
N,P
I,M,
X,Y,,
P,R,,,E,9
...尽管您可能需要使用文字换行符来代替n
in .../\1\n/3
。
答案4
我会用perl
perl -F, -lane '@F[2,3]=""; print join ",", @F'
这使用-a
自动分割,并使用-F
逗号作为字段分隔符。-n
按行迭代 STDIN。然后-e
指定一个脚本来替换字段 2 和 3(perl 从零开始)并打印结果。
-l
隐式删除和添加行结尾。