我正在尝试编写一个查看字符串列表的函数,并确定列表中的下一个字符串是否是前一个字符串的子字符串。
所以,如果我有一个['Ryan', 'Rya', 'Ry', 'Testing', 'Test']
我会回来['Ryan', 'Rya', 'Ry', 'Test']
。
我不确定从哪里开始。
答案 0 :(得分:8)
您可以使用列表推导来完成此任务
def find_results(seq): #I'm sure you can name this function better
return [seq[0]] + [current for previous, current in zip(seq, seq[1:])
if current in previous]
除了第一个元素之外, seq[1:]
是你的整个列表
zip(a, b)
为您传递的每个可迭代项生成元素对。在这种情况下,前面的字符串和当前字符串。
in
运算符将测试一个字符串是否在另一个字符串内。 "test" in "testing"
是真的
理解说,对于每对字符串(当前和前一个),如果当前字符串是前一个字符串的子字符串,则构造所有当前字符串的列表
答案 1 :(得分:3)
你可以这样做:
def f(lst):
yield lst[0]
for i in range(1, len(lst)):
prev_string = lst[i - 1]
curr_string = lst[i]
if curr_string in prev_string:
yield curr_string
f
将成为生成器,因此要将其转换为列表,请将其传递给list
:
In [36]: f(['Ryan', 'Rya', 'Ry', 'Testing', 'Test'])
Out[36]: <generator object f at 0x02F75F08>
In [37]: list(f(['Ryan', 'Rya', 'Ry', 'Testing', 'Test']))
Out[37]: ['Ryan', 'Rya', 'Ry', 'Test']
答案 2 :(得分:2)
你可以这样做:
l = ['Ryan', 'Rya', 'Ry', 'Testing', 'Test']
r = []
for i in range(1, len(l)):
if l[i] in l[i - 1]:
r.append(l[i])
或列表理解:
r = [l[i] for i in range(1,len(l)) if l[i] in l[i - 1]]
答案 3 :(得分:1)
受Ryan Haining's answer的启发,我编写了一个基于生成器的版本,它适用于任何迭代,而不仅仅是序列:
#!/usr/bin/env python2
from itertools import izip, tee
def find_results(iterable):
icur, iprev = tee(iterable)
yield next(icur)
for i in (cur for cur, prev in izip(icur, iprev) if cur in prev):
yield i
print list(find_results(['Ryan', 'Rya', 'Ry', 'Testing', 'Test']))
Python 3版本有点短:
#!/usr/bin/env python3
from itertools import tee
def find_results(iterable):
icur, iprev = tee(iterable)
yield next(icur)
yield from (cur for cur, prev in zip(icur, iprev) if cur in prev)
print(list(find_results(['Ryan', 'Rya', 'Ry', 'Testing', 'Test'])))
答案 4 :(得分:1)
受到@CristianCiupitu的启发,除了我觉得他写的方式令人困惑。这是它的简化版本。
>>> from itertools import izip, tee
>>> def find_results(iterable):
a, b = tee(iterable)
yield next(a)
for cur, prev in izip(a, b):
if cur in prev:
yield cur
>>> print(list(find_results(['Ryan', 'Rya', 'Ry', 'Testing', 'Test'])))
['Ryan', 'Rya', 'Ry', 'Test']