Regex for all strings not containing a string?
好吧,这是一件非常愚蠢的事情,但这是我从来没有学会做的事情,这是一件麻烦事。
如何指定不包含其他字符序列的字符串。例如,我想匹配不以".config"结尾的所有行
我想我可以
1 | .*[^(\.config)]$ |
但这不管用(为什么不呢?)
我知道我能做到
1 | .*[^\.][^c][^o][^n][^f][^i][^g]$ |
但是请告诉我有更好的方法
您可以使用反向查找,例如:
1 | .*(?<!\.config)$ |
除了以".config"结尾的字符串外,它匹配所有字符串。
你的问题有两个问题,所以这里有几个答案。
匹配根本不包含特定字符串的行(如
1 2 3 | ^(?:(?!\.config).)*$ ? ? |
匹配不以特定字符串结尾的行:
1 2 3 | ^.*(?<!\.config)$ ? ? |
还有,作为奖励:匹配不以特定字符串开头的行:
1 2 3 | ^(?!\.config).*$ ? ? |
(如果有,每次包括换行符。
哦,为了回答为什么你的版本不起作用:
1 | (?<!\.config)$ |
:)
正如您所要求的"更好的方法":我将尝试"过滤"方法。我觉得很容易阅读和理解:
1 2 3 4 5 6 | #!/usr/bin/perl while(<>) { next if /\.config$/; # ignore the line if it ends with".config" print; } |
如您所见,我使用了Perl代码作为示例。但我想你明白了吗?
补充:这种方法还可以用于链接更多的过滤模式,并且仍然保持良好的可读性和易于理解。
1 2 3 4 5 6 | next if /\.config$/; # ignore the line if it ends with".config" next if /\.ini$/; # ignore the line if it ends with".ini" next if /\.reg$/; # ignore the line if it ends with".reg" # now we have filtered out all the lines we want to skip ... process only the lines we want to use ... |
通过使用
使用否定的lookahead(使用perl regexs),比如:
除非你是"伟大的"…既然您没有使用匹配结果,为什么不搜索以.config结尾的字符串并跳过它们呢?在Python中:
1 2 3 4 | import re isConfig = re.compile('\.config$') # List lst is given filteredList = [f.strip() for f in lst if not isConfig.match(f.strip())] |
我怀疑这会比更复杂的RE运行得更快。
在找到这个页面之前,我使用了ReXExpAL,并在检查字符串不包含文件扩展名时提出了以下解决方案:
因此,要找到一个不包含另一个
我关于这个特殊regex用法的文章