Python:拆分字符串并获取位置

5
我希望将一个字符串分割成若干部分,并且获取每个部分的起始位置。可以使用以下代码实现:
str_ = '  d     A7    g7'
flag_non_space_string_started = False
positions = []
for i, letter in enumerate(str_):
    if letter is not ' ':
        if not flag_non_space_string_started:
            positions.append(i)
            flag_non_space_string_started = True
    else:
        flag_non_space_string_started = False
# this is what I want
print(str_.split())
print(positions)
# prints:
# ['d', 'A7', 'g7']
# [2, 8, 14]

有没有更短(更符合Python风格)的方法来获取这些位置?

1
短并不等同于Pythonic。通常情况下,缩短代码会使其更难理解。 - user
1个回答

6

您可以在此处使用 itertools.groupbyenumerate。我们使用 not str.isspace 分组白色空格,所以对于非空格字符而言,k 为真值,空格则为假值,因此需要使用 if k 条件。由于每个分组都是迭代器,我们需要调用 next() 函数来获取起始索引和第一个字符。然后使用列表推导式来获取组中其余的项目,并将其传递给 str.join() 函数以获取字符串。别忘了在此字符串前面添加我们之前弹出的项目:

from itertools import groupby

str_ = '  d     A7    g7'

for k, g in groupby(enumerate(str_), lambda x: not x[1].isspace()):
    if k:
        pos, first_item = next(g)
        print pos, first_item + ''.join([x for _, x in g])

输出:

2 d
8 A7
14 g7

如果上述解决方案看起来很复杂,那么可以使用re.finditer。由re.finditer返回的匹配对象具有像.start()和group()这样的方法,它们分别对应于匹配组的起始索引和组本身。
import re

str_ = '  d     A7    g7'

for m in re.finditer(r'\S+', str_):
    index, item = m.start(), m.group()
    # now do something with index, item

1
OP似乎实际上想要两个单独的列表,因此需要进行更多的工作,而不仅仅是re.finditer - Padraic Cunningham
@PadraicCunningham 更多的只是一个zip*调用。 - Ashwini Chaudhary
@PadraicCunningham Indices, items = map(list, zip(*LC)),或者使用简单的循环re.finditer,然后跟随append调用两个列表也可以。让我们把这个练习留给OP。 - Ashwini Chaudhary
@AshwiniChaudhary,不要误会,这与个人无关。我之所以给你的帖子点了踩,只是因为它让人误认为“短小而复杂的代码就是好代码”。 - user
@user5061 为什么你认为是我给你的投票点了踩🤔 - Ashwini Chaudhary
显示剩余4条评论

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接