我有一个巨大的python列表作为下面的例子:
ls = ['name: John', 'John has ', '4 yellow ', 'cars.', 'name: Angelina', 'Angelina has ', '5 yellow', 'cars.']
我想把这些信息以这种格式连接起来:
ls = ['name: John', 'John has 4 yellow cars.', 'name: Angelina', 'Angelina has 5 yellow cars.']
我已经试过这个代码
with open ('names.txt', 'r') as text:
lines = text.readlines()
for index,line in enumerate(lines):
if not linha.startswith('name:'):
ls2.append(lines[index]+lines[index+1])
但这并不好,因为我有这样的东西:
ls = ['name: John', 'John has 4 yellow', '4 yellow cars.', 'cars.name: Angelina']
你知道我该怎么做这个任务吗?
您可以使用itertools.groupby
:
import itertools
ls = ['name: John', 'John has ', '4 yellow ', 'cars.', 'name: Angelina', 'Angelina has ', '5 yellow', 'cars.']
g = itertools.groupby(ls, lambda x: x.startswith('name: '))
output = [''.join(v) for _, v in g]
print(output) # ['name: John', 'John has 4 yellow cars.', 'name: Angelina', 'Angelina has 5 yellowcars.']
根据每个项目是否以'name: '
开头对项目进行分组;
- 以
'name: '
开头的项组成一组(即['name: John']
)。 - 下面几个不这样做的项目组成一个组(即
['John has ', '4 yellow ', 'cars.']
)。 - 下一个这样做的项目形成另一组(
['name: Angelina']
)。 - …等等。
然后join
将每组中的字符串连接起来。
将变量中不以name:
开头的所有行连接起来,然后在到达下一个name:
行时将其附加到结果中。
ls2 = []
temp_string = ''
for line in lines:
line = line.rstrip('n')
if line.startswith('name:'):
if temp_string:
ls2.append(temp_string)
temp_string = ''
ls2.append(line)
else:
temp_string += line
# append the last set of lines
if temp_string:
ls2.append(temp_string)
我认为逻辑可以更好地表达为"如果当前行以name:
开始,然后将其附加到一个新的列表中,并将接下来的三行连接成一行,并将该行也附加。">
with open ('names.txt', 'r') as text:
lines = text.readlines()
i = 0
ls2 = []
for i, line in enumerate(lines):
if line.startswith('name:'):
ls2.append(line)
ls2.append(lines[i+1] + lines[i+2] + lines[i+3])
也许不分割成所有行,但只是按名称行分割整个文件,然后抛光空白?
import re
with open('names.txt') as f:
ls = [re.sub(r's+', ' ', s.strip())
for s in re.split('(name:.*)', f.read())
if s]
将您的列表写回文件并使用上面的代码,我得到了所需的输出(应该有空格但没有重复的空格):
['name: John', 'John has 4 yellow cars.', 'name: Angelina', 'Angelina has 5 yellow cars.']
上网试试!