使用sed或awk - 或其他文本处理器 - 来查找/替换范围内的数字

时间:2012-11-25 01:15:53

标签: sed awk grep

我是正则表达式和处理文本的初学者。我需要做的是将文件中的文本格式化为CSV格式以导入电子表格。

我需要找到一个具有特定范围的数字并在其后面插入回车符\r并删除逗号。我知道如何查找/替换特定字符,但不是在一系列字符或数字中。

这是交易:我有一个长文本文件,采用这种格式。

Shimshon A
(blank)
November 24, 2012
13,481
jonathan t
Laguna Niguel, CA
November 24, 2012
13,480
scott b
Sussex, NJ
November 24, 2012
13,479

我在带有find / replace的文本编辑器中添加了行尾逗号和行引号的开头/结尾:

"Shimshon A",
"(blank)",
"November 24, 2012",
"13,481",
"jonathan t",
"Laguna Niguel, CA",
"November 24, 2012",
"13,480",
"scott b",
"Sussex, NJ",
"November 24, 2012",
"13,479",

但是一旦我删除所有返回后,我需要在13,481到1范围内的数字之后插入一个返回。这是因为CSV中的每一列都需要是Name,Location,Date和Number,如下所示:

"Shimshon A","(blank)","November 24, 2012","13,481"
"jonathan t","Laguna Niguel, CA","November 24, 2012","13,480"
"scott b","Sussex, NJ","November 24, 2012","13,479"

1 个答案:

答案 0 :(得分:6)

解决此问题的另一种方法是将数据集视为四行组

使用awk

awk 'NR%4!=0 { printf "%s", $0; next } { sub(/,$/,"") }1' file

结果:

"Shimshon A","(blank)","November 24, 2012","13,481"
"jonathan t","Laguna Niguel, CA","November 24, 2012","13,480"
"scott b","Sussex, NJ","November 24, 2012","13,479"

说明:

正如您所看到的,这使用modulus operator来'grep'每条完全可以被4整除的行(即不是整数)。 'printf'语句将这些行相互打印在一起。 'next'成功时会跳过。在所有其他时间,删除滞后的逗号,并打印行(默认情况下,语句末尾的1是速记打印)。有任何问题,请随时询问。 HTH。

您还可以通过简单地更改printf语句来集成添加逗号和双引号:

awk 'NR%4!=0 { printf "\"%s\",", $0; next } { printf "\"%s\"\n", $0 }' file

使用GNU sed

sed -n 'N;N;N;s/\n\|,$//g;p' file

或者在添加逗号和双引号之前:

sed -n 'N;N;N;s/^\|$/"/g;s/\n/","/g;p' file

结果:

"Shimshon A","(blank)","November 24, 2012","13,481"
"jonathan t","Laguna Niguel, CA","November 24, 2012","13,480"
"scott b","Sussex, NJ","November 24, 2012","13,479"

说明:

虽然此解决方案要短得多,但它与上面使用awk描述的情绪相同。对于第一个sed语句:使用-n标志禁用默认打印。在样式空间中附加三行。在第四行,删除换行符和滞后逗号。然后打印。

第二个sed声明大致相同;在模式空间中添加三行。在第四行,用双引号替换行的开头和结尾。同时用双引号,逗号,双引号替换换行符;全球。然后打印。 HTH。


来自评论:

根据我的经验,使用awk排序(尽管可能)可能会很难快速阅读。这是一种让您重复使用我们之前使用其他两个工具pastesort编写的代码的方法:

paste <(awk -F, 'NR%4==2 { print $NF }' file) <(awk 'NR%4!=0 { printf "\"%s\",", $0; next } { printf "\"%s\"\n", $0 }' file) | sort | sed 's/[^"]*//'

应该注意,此命令在添加逗号和双引号之前使用输入 - 如您所见,它使用上述第二个awk命令。它的工作原理是在我们之前获得的每个结果之前粘贴(paste)'state'。然后,这允许使用sort按字母顺序对行进行排序。输入排序后,sed用于删除此信息。