我正在尝试使用非常基本的技能集在 python 字符串中查找字符的所有索引号。例如,如果我有字符串“Apples are fully awesome”,并且我想找到字符串中 'a' 的位置。我的理想输出是:
0
7
14
19
Run Code Online (Sandbox Code Playgroud)
这些是字符串中出现“a”的所有位置(我认为)
这是我到目前为止的代码:
sentence = input("Input a string: ")
for ch in sentence:
x = sentence.find('o')
print(x)
Run Code Online (Sandbox Code Playgroud)
在这里,我正在寻找 'o' 而不是 a。我的想法是,对于字符串中的每个字符,find 函数都会返回 'o' 的位置。因为我不知道输入字符串需要多长时间,所以我使用了 for 循环。我能够找到并打印出“o”的第一个实例,但不是全部。我该怎么办?提前致谢!
使用enumerate是标准的方法。不过,您可以利用 速度来str.find进行时间紧迫的操作。
def find_all(s, c):
idx = s.find(c)
while idx != -1:
yield idx
idx = s.find(c, idx + 1)
print(*find_all('Apples are totally awesome', 'o')) # 12 23
Run Code Online (Sandbox Code Playgroud)
为了优雅和考虑非常大的字符串,我使上面的返回一个生成器。list如果需要,当然可以将它转换为 a 。
这是针对使用enumerate和列表理解的解决方案的基准。两种解决方案都具有线性时间复杂度,但str.find速度明显更快。
import timeit
def find_all_enumerate(s, c):
return [i for i, x in enumerate(s) if c == 'a']
print(
'find_all:',
timeit.timeit("list(find_all('Apples are totally awesome', 'o'))",
setup="from __main__ import find_all")
)
print(
'find_all_enumerate:',
timeit.timeit("find_all_enumerate('Apples are totally awesome', 'o')",
setup="from __main__ import find_all_enumerate")
)
Run Code Online (Sandbox Code Playgroud)
find_all: 1.1554179692960915
find_all_enumerate: 1.9171753468076869
Run Code Online (Sandbox Code Playgroud)
这是enumerate的好地方,它允许我们在循环时获得index and item,所以如果我们匹配item我们可以得到相应的index,它也有助于.lower()避免匹配案例的问题
s = 'Apples are totally awesome'
l = [idx for idx, item in enumerate(s.lower()) if 'o' in item]
Run Code Online (Sandbox Code Playgroud)
扩展循环:
l = []
for idx, item in enumerate(s.lower()):
if 'o' in item:
l.append(idx)
Run Code Online (Sandbox Code Playgroud)
Run Code Online (Sandbox Code Playgroud)/python/stack$ python3.7 sum.py [12, 23]