如果我有一个字符串,比如"The quick brown fox jumps over the lazy dog"
,并且有一个列表[1, 8, 14, 18, 27]
表示在哪里剪切字符串。
我期望得到的是一个包含剪切字符串部分的列表。对于此示例,输出应为:
['T', 'he quic', 'k brow', 'n fo', 'x jumps o', 'ver the lazy dog']
我直观而天真的方法是简单地编写for循环,记住上一个索引,切片并将切片附加到输出。
_str="The quick brown fox jumps over the lazy dog"
cut=[1, 8, 14, 18, 27]
prev=0
out=[]
for i in cut:
out.append(_str[prev:i])
prev=i
out.append(_str[prev:])
还有更好的方法吗?
答案 0 :(得分:11)
这是我将如何做到的:
import matplotlib.pyplot as plt
plt.figure(figsize=(8, 6))
sns.factorplot("MONTH", "VALUE", hue="REGION", data=typessns, kind="box", palette="OrRd"); // OR any plot code
一些解释:
我在前面添加0,在列表末尾添加>>> s = "The quick brown fox jumps over the lazy dog"
>>> l = [1, 8, 14, 18, 27]
>>> l = [0] + l + [len(s)]
>>> [s[x:y] for x,y in zip(l, l[1:])]
['T', 'he quic', 'k brow', 'n fo', 'x jumps o', 'ver the lazy dog']
,这样
len(s)
给了我一系列切片索引元组。剩下要做的就是在列表解析中解压缩这些索引并生成你想要的切片。
编辑:
如果真的关心此操作的内存占用,因为您经常处理非常大的大字符串和列表,请一直使用生成器并构建列表>>> zip(l, l[1:])
[(0, 1), (1, 8), (8, 14), (14, 18), (18, 27), (27, 43)]
这样它首先包含0和l
。
对于Python 2:
len(s)
对于Python 3:
>>> from itertools import izip, tee
>>> s = "The quick brown fox jumps over the lazy dog"
>>> l = [0, 1, 8, 14, 18, 27, 43]
>>>
>>> def get_slices(s, l):
... it1, it2 = tee(l)
... next(it2)
... for start, end in izip(it1, it2):
... yield s[start:end]
...
>>> list(get_slices(s,l))
['T', 'he quic', 'k brow', 'n fo', 'x jumps o', 'ver the lazy dog']
执行zip
在Python 2中所做的事情(参见Python 3.3版本)
对于使用izip
语法的Python 3.3+:
yield from
答案 1 :(得分:1)
递归方法:
def split(cut,str):
if cut:
b=cut.pop()
return split(cut,str[:b])+[str[b:]]
return [str]
答案 2 :(得分:1)
您可以使用生成器功能:
def sli(s, inds):
it = iter(inds)
p = next(it)
yield s[:p]
for i in it:
yield s[p:i]
p = i
yield s[p:]
print(list(sli(_str, cut)))
['T', 'he quic', 'k brow', 'n fo', 'x jumps o', 'ver the lazy dog']
创建一个可以懒惰评估的切片列表。
除非您需要空字符串列表,否则还需要考虑传递空字符串:
def sli(s, inds):
if not s:
return
it = iter(inds)
p = next(it)
yield s[:p]
for i in it:
yield s[p:i]
p = i
yield s[p:]
除了更强大,使用更少,内存也更快:
Python3:
l = sorted(random.sample(list(range(5000)), 1000))
_l = [0] + l + [len(s)]
[s[x:y] for x,y in zip(_l, _l[1:])]
....:
1000 loops, best of 3: 368 µs per loop
In [39]: timeit list(sli(s, l))
1000 loops, best of 3: 311 µs per loop
Python2:
In [8]: s = "The quick brown fox jumps over the lazy dog"
In [9]: s *= 1000
In [10]: l = sorted(random.sample(list(range(5000)), 1000))
In [11]: %%timeit
_l = [0] + l + [len(s)]
[s[x:y] for x,y in zip(_l, _l[1:])]
....:
1000 loops, best of 3: 321 µs per loop
In [12]: timeit list(sli(s, l))ched
1000 loops, best of 3: 204 µs per loop
编写自己的函数是完全pythonic的,在这种情况下比尝试将代码压缩到几行更有效。