用Python连接前后句子

2 投票
4 回答
1424 浏览
提问于 2025-04-16 00:09

我正在尝试把一组句子连接在一起,这些句子保存在一个 list 里。我有一个函数可以判断一个句子是否值得保存。不过,为了保持句子的上下文,我还需要保留它前面的句子和后面的句子。如果是边界情况,比如第一个句子或最后一个句子,我就只保留这个句子和它唯一的邻居。

举个例子比较好:

    ex_paragraph = ['The quick brown fox jumps over the fence.', 
                   'Where there is another red fox.', 
                   'They run off together.', 
                   'They live hapily ever after.']
    t1 = lambda x: x.startswith('Where')
    t2 = lambda x: x'startswith('The ')

对于 t1,结果应该是:

['The quick brown fox jumps over the fence. Where there is another red fox. They run off together.']

对于 t2,结果应该是:

['The quick brown fox jumps over the fence. Where there is another red fox.']

我的解决方案是:

def YieldContext(sent_list, cont_fun):
    def JoinSent(sent_list, ind):
        if ind == 0:
            return sent_list[ind]+sent_list[ind+1]
        elif ind == len(sent_list)-1:
            return sent_list[ind-1]+sent_list[ind]
        else:

            return ' '.join(sent_list[ind-1:ind+1])


    for sent, sentnum in izip(sent_list, count(0)):
        if cont_fun(sent):
            yield JoinSent(sent_list, sent_num)

有没有人知道更“干净”或者更符合 Python 风格的方法来做这样的事情?这个 if-elif-else 看起来有点勉强。

谢谢,

Will

PS. 我显然是在用一个更复杂的“上下文函数”,但这只是一个简单的例子。

4 个回答

1

我可能会这样做:

from itertools import izip, tee
prev, this, next = tee([''] + ex_paragraph + [''], 3)
this.next()
next.next()
next.next()
[' '.join(ctx).strip() for ctx in izip(prev, this, next) if cont_fun(this)]

这里的 cont_fun 可以是 t1 或者 t2 其中之一。

1

好吧,我可能只会把条件语句写成一行:

def join_send(sent_list, ind):
    items = [sent_list[i] for i in (ind-1, ind, ind+1) if i >= 0 and i < len(sent_list)]
    return ' '.join(items)

不过,这样写可能有人会觉得不太好读。

附言:更符合Python风格的写法应该是用PEP 8的命名方式,比如说yield_context。或者在某些库里,yieldContext也是可以的……但是YieldContext就有点奇怪了?

4

在列表的开头和结尾加一个空字符串其实是个不错的主意,但其实没必要用那些复杂的列表推导式。你可以很简单地创建一个生成器:

def yieldContext(l, func):
    l = [''] + l + ['']
    for i, s in enumerate(l):
        if func(s):
            yield ' '.join(l[i-1:i+2]).strip()

这样会得到:

>>> print list(yieldContext(ex_paragraph, t1))
['The quick brown fox jumps over the fence. Where there is another red fox. They run off together.']

>>> print list(yieldContext(ex_paragraph, t2))
['The quick brown fox jumps over the fence. Where there is another red fox.']

(如果你真的想创建一个列表,其实差别不大。主要还是看你有多少句子,以及你想怎么处理这些“上下文”)

def yieldContext(l, func):
    l = [''] + l + ['']
    return [' '.join(l[i-1:i+2]).strip() for i, s in enumerate(l) if func(s)]

撰写回答