This question already has an answer here:
这个问题已经有了答案:
- Regular expression to match a line that doesn't contain a word? 25 answers
- 正则表达式匹配一个不包含单词的行?25的答案
Ok, so this is something completely stupid but this is something I simply never learned to do and its a hassle.
好吧,这是完全愚蠢的事情,但这是我从来没有学会做的事情,也是一件麻烦事。
How do I specify a string that does not contain a sequence of other characters. For example I want to match all lines that do NOT end in '.config'
如何指定不包含其他字符序列的字符串。例如,我想要匹配所有不以'.config'结尾的行。
I would think that I could just do
我认为我能做到。
.*[^(\.config)]$
but this doesn't work (why not?)
但这行不通(为什么不呢?)
I know I can do
我知道我能做到。
.*[^\.][^c][^o][^n][^f][^i][^g]$
but please please please tell me that there is a better way
但是请告诉我有一个更好的方法。
7 个解决方案
#1
41
You can use negative lookbehind, e.g.:
你可以用消极的眼神,例如:
.*(?<!\.config)$
This matches all strings except those that end with ".config"
除了以“.config”结尾的字符串之外,这将匹配所有字符串
#2
15
Your question contains two questions, so here are a few answers.
你的问题包含两个问题,所以这里有几个答案。
Match lines that don't contain a certain string (say .config
) at all:
不包含特定字符串(比如.config)的匹配行:
^(?:(?!\.config).)*$\r?\n?
Match lines that don't end in a certain string:
匹配不以特定字符串结束的行:
^.*(?<!\.config)$\r?\n?
and, as a bonus: Match lines that don't start with a certain string:
而且,作为一个额外的奖励:匹配不以特定字符串开始的行:
^(?!\.config).*$\r?\n?
(each time including newline characters, if present.
(每一次包括换行符,如果存在。
Oh, and to answer why your version doesn't work: [^abc]
means "any one (1) character except a, b, or c". Your other solution would also fail on test.hg
(because it also ends in the letter g - your regex looks at each character individually instead of the entire .config
string. That's why you need lookaround to handle this.
噢,要回答为什么你的版本不起作用:[abc]意为“除了a、b、c之外的任何一个字符”。您的其他解决方案也会在测试中失败。hg(因为它也以字母g结尾),你的regex会单独查看每个字符,而不是整个.config字符串。这就是为什么你需要到处看看来处理这个问题。
#3
4
(?<!\.config)$
:)
:)
#4
2
By using the [^]
construct, you have created a negated character class, which matches all characters except those you have named. Order of characters in the candidate match do not matter, so this will fail on any string that has any of [(\.config)
(or [)gi.\onc(]
)
通过使用[]构造,您创建了一个被否定的字符类,它与您所指定的所有字符相匹配。候选匹配中的字符顺序无关紧要,因此在任何具有[(\.config)(或[)gi.\onc(])的字符串上都将失败。
Use negative lookahead, (with perl regexs) like so: (?!\.config$)
. This will match all strings that do not match the literal ".config"
使用negative lookahead(使用perl regexs): (? \.config$)。这将匹配与文字“.config”不匹配的所有字符串。
#5
2
Unless you are "grepping" ... since you are not using the result of a match, why not search for the strings that do end in .config and skip them? In Python:
除非你在“准备”……既然您没有使用匹配的结果,为什么不搜索在.config中结束的字符串并跳过它们呢?在Python中:
import re
isConfig = re.compile('\.config$')
# List lst is given
filteredList = [f.strip() for f in lst if not isConfig.match(f.strip())]
I suspect that this will run faster than a more complex re.
我怀疑这将比一个更复杂的re运行得更快。
#6
2
As you have asked for a "better way": I would try a "filtering" approach. I think it is quite easy to read and to understand:
正如您所要求的“更好的方法”:我将尝试“过滤”方法。我认为阅读和理解是很容易的:
#!/usr/bin/perl
while(<>) {
next if /\.config$/; # ignore the line if it ends with ".config"
print;
}
As you can see I have used perl code as an example. But I think you get the idea?
正如您所看到的,我使用了perl代码作为示例。但我认为你明白了吗?
added: this approach could also be used to chain up more filter patterns and it still remains good readable and easy to understand,
添加:这种方法也可以用来连接更多的过滤模式,而且它仍然保持良好的可读性和易于理解,
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 ...
#7
0
I used Regexpal before finding this page and came up with the following solution when I wanted to check that a string doesn't contain a file extension:
在找到这个页面之前,我使用了Regexpal,并在我想要检查一个字符串是否包含文件扩展名时找到了下面的解决方案:
^(.(?!\.[a-zA-Z0-9]{3,}))*$
I used the m
checkbox option so that I could present many lines and see which of them did or did not match.
^(。(? ! \[a-zA-Z0-9]{ 3 }))*我使用了美元复选框选项,以便我能现在很多行,看看哪些人或不匹配。
so to find a string that doesn't contain another "^(.(?!" +
expression you don't want + "))*$"
因此,要找到一个不包含另一个字符串的字符串(?!)+表达你不想要+ ")*$"
My article on the uses of this particular regex
我的文章关于使用这个特殊的正则表达式。
#1
41
You can use negative lookbehind, e.g.:
你可以用消极的眼神,例如:
.*(?<!\.config)$
This matches all strings except those that end with ".config"
除了以“.config”结尾的字符串之外,这将匹配所有字符串
#2
15
Your question contains two questions, so here are a few answers.
你的问题包含两个问题,所以这里有几个答案。
Match lines that don't contain a certain string (say .config
) at all:
不包含特定字符串(比如.config)的匹配行:
^(?:(?!\.config).)*$\r?\n?
Match lines that don't end in a certain string:
匹配不以特定字符串结束的行:
^.*(?<!\.config)$\r?\n?
and, as a bonus: Match lines that don't start with a certain string:
而且,作为一个额外的奖励:匹配不以特定字符串开始的行:
^(?!\.config).*$\r?\n?
(each time including newline characters, if present.
(每一次包括换行符,如果存在。
Oh, and to answer why your version doesn't work: [^abc]
means "any one (1) character except a, b, or c". Your other solution would also fail on test.hg
(because it also ends in the letter g - your regex looks at each character individually instead of the entire .config
string. That's why you need lookaround to handle this.
噢,要回答为什么你的版本不起作用:[abc]意为“除了a、b、c之外的任何一个字符”。您的其他解决方案也会在测试中失败。hg(因为它也以字母g结尾),你的regex会单独查看每个字符,而不是整个.config字符串。这就是为什么你需要到处看看来处理这个问题。
#3
4
(?<!\.config)$
:)
:)
#4
2
By using the [^]
construct, you have created a negated character class, which matches all characters except those you have named. Order of characters in the candidate match do not matter, so this will fail on any string that has any of [(\.config)
(or [)gi.\onc(]
)
通过使用[]构造,您创建了一个被否定的字符类,它与您所指定的所有字符相匹配。候选匹配中的字符顺序无关紧要,因此在任何具有[(\.config)(或[)gi.\onc(])的字符串上都将失败。
Use negative lookahead, (with perl regexs) like so: (?!\.config$)
. This will match all strings that do not match the literal ".config"
使用negative lookahead(使用perl regexs): (? \.config$)。这将匹配与文字“.config”不匹配的所有字符串。
#5
2
Unless you are "grepping" ... since you are not using the result of a match, why not search for the strings that do end in .config and skip them? In Python:
除非你在“准备”……既然您没有使用匹配的结果,为什么不搜索在.config中结束的字符串并跳过它们呢?在Python中:
import re
isConfig = re.compile('\.config$')
# List lst is given
filteredList = [f.strip() for f in lst if not isConfig.match(f.strip())]
I suspect that this will run faster than a more complex re.
我怀疑这将比一个更复杂的re运行得更快。
#6
2
As you have asked for a "better way": I would try a "filtering" approach. I think it is quite easy to read and to understand:
正如您所要求的“更好的方法”:我将尝试“过滤”方法。我认为阅读和理解是很容易的:
#!/usr/bin/perl
while(<>) {
next if /\.config$/; # ignore the line if it ends with ".config"
print;
}
As you can see I have used perl code as an example. But I think you get the idea?
正如您所看到的,我使用了perl代码作为示例。但我认为你明白了吗?
added: this approach could also be used to chain up more filter patterns and it still remains good readable and easy to understand,
添加:这种方法也可以用来连接更多的过滤模式,而且它仍然保持良好的可读性和易于理解,
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 ...
#7
0
I used Regexpal before finding this page and came up with the following solution when I wanted to check that a string doesn't contain a file extension:
在找到这个页面之前,我使用了Regexpal,并在我想要检查一个字符串是否包含文件扩展名时找到了下面的解决方案:
^(.(?!\.[a-zA-Z0-9]{3,}))*$
I used the m
checkbox option so that I could present many lines and see which of them did or did not match.
^(。(? ! \[a-zA-Z0-9]{ 3 }))*我使用了美元复选框选项,以便我能现在很多行,看看哪些人或不匹配。
so to find a string that doesn't contain another "^(.(?!" +
expression you don't want + "))*$"
因此,要找到一个不包含另一个字符串的字符串(?!)+表达你不想要+ ")*$"
My article on the uses of this particular regex
我的文章关于使用这个特殊的正则表达式。