我正在尝试删除一行中没有前缀为\
的特殊字符。
以下是特殊字符:
^$%.*+?!(){}[]|\
我需要在第二列中检查所有上面没有\
前缀的特殊字符。
我正在尝试使用awk
完成此操作,但没有运气。我想要输出如下。
input.txt中
1,ap^ple
2,o$range
3,bu+tter
4,gr(ape
5,sm\(oke
6,ra\in
7,pla\\y
8,wor\+k
output.txt的
1,ap^ple
2,o$range
3,bu+tter
4,gr(ape
6,ra\in
答案 0 :(得分:2)
我相信你只是在寻找:
awk '$2 !~ /\\[][|\\{}()!?+*.%$^]/' FS=,
这给出了给定输入文件的所需输出,但完全不符合问题中给出的描述。
修改
鉴于评论部分的讨论,似乎所需的解决方案应该输出包含特殊字符的所有行,除非该字符前面有反斜杠。鉴于该描述,我们必须从特殊字符列表中删除反斜杠。 A(非工作,为描述目的而给出)解决方案是:
awk '$2 ~ /[^\\][][|{}()!?+*.%$^]/' FS=,
这简单地匹配任何两个字符串,其中第一个不是反斜杠,第二个是字符][|{}()!?+*.%$^
之一。这会失败,因为它不会捕获作为字符串的第一个元素出现特殊字符的情况。为此,我们扩展正则表达式,以便第一个字符可以是字符串的开头或任何不是反斜杠的字符。
awk '$2 ~ /(^|[^\\])[][|{}()!?+*.%$^]/' FS=,
我们需要重新排序特殊字符的原因是]
在括号内具有特殊含义(即,它关闭括号!)并且必须首先列出以避免该含义。类似地,^
必须不,因为它是字符类的第一个成员(它否定了类)时具有特殊含义。 (其他角色并不重要;它们只是作为印刷事故重新订购。)
答案 1 :(得分:1)
诀窍的一部分是将特殊字符安全地放入角色类中,记住]
,^
和-
(列表中没有)具有相关的特殊规则与他们在角色类。具体来说,^
作为第一个字符否定了字符类(所以将它放在除第一个之外的某个地方),]
字符终止字符类,除非它是{{1}之后的第一个或第二个字符。 }。
因此,你想要:
^
复杂(可怕)正则表达式匹配反斜杠后跟一个特殊字符;操作是awk '/\\[]^$%.*+?!(){}[\\|]/ { next } { print }' input.txt
以跳过该行。 next
(也可以写成{ print }
或任何其他真值)打印那些未被正则表达式消除的行。
示例输出
1
您可以优化处理以忽略第一个字段,依此类似于William Pursell的answer,它对列表中字符的重新排序与我的方式基本相同,但没有解释原因。
1,ap^ple
2,o$range
3,bu+tter
4,gr(ape
6,ra\in