5

有没有办法找出一个字符串是否包含python集合中的任何一个字符?

使用单个字符很简单,但我需要检查字符串是否包含一组坏字符中的任何一个。

具体来说,假设我有一个字符串:

s = 'amanaplanacanalpanama~012345'

我想看看字符串是否包含任何元音:

bad_chars = 'aeiou'

并在 for 循环中为文件中的每一行执行此操作:

if [any one or more of the bad_chars] in s:
    do something

我正在扫描一个大文件,所以如果有更快的方法,那将是理想的。此外,并非必须检查每个坏字符——只要遇到足以结束搜索的字符即可。

我不确定是否有内置函数或简单的方法来实现它,但我还没有遇到任何东西。任何指针将不胜感激!

4

5 回答 5

9
any((c in badChars) for c in yourString)

或者

any((c in yourString) for c in badChars)  # extensionally equivalent, slower

或者

set(yourString) & set(badChars)  # extensionally equivalent, slower

“只要遇到一个就足以结束搜索。” - 如果您使用第一种方法,这将是正确的。

您说您关心性能:除非您处理大量数据,否则性能不应该成为问题。如果遇到问题,可以尝试:


正则表达式

编辑以前我在这里写了一个关于使用正则表达式的部分,通过re模块,以编程方式生成一个由单个字符类[...]和 using组成的正则表达式,.finditer但需要注意的是,在一切可能无法正常工作之前放置一个简单的反斜杠。确实,经过测试,是这样的,我绝对不会推荐这种方法。使用它需要对正则表达式字符类的整个(稍微复杂的)子语法进行逆向工程(例如,您可能有字符 like\后跟w, like ]or [, or like -,而仅仅转义一些 like\w可能会给它一个新的含义)。


根据操作是 O(1) 还是 O(N) ,如果您有很多 badChar str.__contains__,首先将您的文本/行转换为一组以确保操作是 O(1) 可能是合理的:in

badCharSet = set(badChars)
any((c in badChars) for c in yourString)

any((c in set(yourString)) for c in badChars)(根据python编译器的智能程度,可以使它成为一个单行代码)


您真的需要逐行执行此操作吗?

对整个文件 O(#badchars) 执行一次此操作可能比对文件 O(#lines*#badchars) 中的每一行执行一次更快,尽管渐近常数可能无关紧要。

于 2012-05-03T22:34:40.193 回答
4

使用python的any函数。

if any((bad_char in my_string) for bad_char in bad_chars):
    # do something 
于 2012-05-03T22:35:25.217 回答
2

这应该非常有效和清晰。它使用集合:

#!/usr/bin/python

bad_chars = set('aeiou')

with open('/etc/passwd', 'r') as file_:
   file_string = file_.read()
file_chars = set(file_string)

if file_chars & bad_chars:
   print('found something bad')
于 2012-05-03T22:48:08.167 回答
1

any这个正则表达式的速度是我最小测试的两倍。您应该使用自己的数据进行尝试。

r = re.compile('[aeiou]')
if r.search(s):
    # do something
于 2012-05-03T22:49:15.130 回答
0

以下 Python 代码应打印出 bad_chars 中的任何字符(如果它存在于 s 中):

for i in vowels:
    if i in your charset:
        #do_something

您还可以使用以下示例使用 python 内置 any:

>>> any(e for e in bad_chars if e in s)
True
于 2012-05-03T22:39:33.427 回答