在字符串中查找字符/单词的周围句子

Posted

技术标签:

【中文标题】在字符串中查找字符/单词的周围句子【英文标题】:Finding the surrounding sentence of a char/word in a string 【发布时间】:2013-03-09 22:50:43 【问题描述】:

我正在尝试使用 python 从包含给定子字符串的字符串中获取句子

我可以访问字符串(学术摘要)和带有开始和结束索引的亮点列表。例如:


  abstract: "...long abstract here..."
  highlights: [
    
      concept: 'a word',
      start: 1,
      end: 10
    
    
      concept: 'cancer',
      start: 123,
      end: 135
    
  ]

我遍历每个亮点,在摘要中找到它的开始索引(结束并不重要,因为我只需要在一个句子中获取一个位置),然后以某种方式需要识别出现索引的句子.

我可以使用nltk.tonenize.sent_tokenize 将摘要标记为句子,但这样做会使索引位置变得无用。

我应该如何解决这个问题?我想正则表达式是一种选择,但 nltk 标记器似乎是一种很好的方法,不使用它会很遗憾。或者通过查找自上一个句号以来的字符数以某种方式重置开始索引/感叹号/问号?

【问题讨论】:

这看起来像 JSON。 是的,我正在处理来自 API 端点的数据。 这可能很昂贵,但您可以遍历句子并根据长度重新计算句子的索引,然后搜索该索引 【参考方案1】:

您是对的,NLTK 标记器确实是您在这种情况下应该使用的,因为它足够强大,可以处理几乎所有句子的定界,包括以“引号”结尾的句子。你可以这样做(paragraph 来自随机生成器):

开始,

from nltk.tokenize import sent_tokenize

paragraph = "How does chickens harden over the acceptance? Chickens comprises coffee. Chickens crushes a popular vet next to the eater. Will chickens sweep beneath a project? Coffee funds chickens. Chickens abides against an ineffective drill."
highlights = ["vet","funds"]
sentencesWithHighlights = []

最直观的方式:

for sentence in sent_tokenize(paragraph):
    for highlight in highlights:
        if highlight in sentence:
            sentencesWithHighlights.append(sentence)
            break

但是使用这种方法,我们实际上有一个有效的 3x 嵌套 for 循环。这是因为我们首先检查每个sentence,然后检查每个highlight,然后检查sentence 中的每个子序列以查找highlight

我们可以得到更好的性能,因为我们知道每个亮点的起始索引:

highlightIndices = [100,169]
subtractFromIndex = 0
for sentence in sent_tokenize(paragraph):
    for index in highlightIndices:
        if 0 < index - subtractFromIndex < len(sentence):
            sentencesWithHighlights.append(sentence)
            break
    subtractFromIndex += len(sentence)

无论哪种情况,我们都会得到:

sentencesWithHighlights = ['Chickens crushes a popular vet next to the eater.', 'Coffee funds chickens.']

【讨论】:

这正是我要找的,简单易懂,谢谢!【参考方案2】:

我假设你所有的句子都以这三个字符之一结尾:!?.

如何循环突出显示列表,创建一个正则表达式组:

(?:list|of|your highlights)

然后将你的整个摘要与这个正则表达式进行匹配:

/(?:[\.!\?]|^)\s*([^\.!\?]*(?:list|of|your highlights)[^\.!\?]*?)(?=\s*[\.!\?])/ig

这样,您将在每场比赛的第一个子组 (RegExr) 中获得包含至少一个亮点的句子。

【讨论】:

【参考方案3】:

另一种选择(虽然很难说它对于可变定义的文本有多可靠)是将文本拆分成一个句子列表并针对它们进行测试:

re.split('(?<=\?|!|\.)\s0,2(?=[A-Z]|$)', text)

【讨论】:

以上是关于在字符串中查找字符/单词的周围句子的主要内容,如果未能解决你的问题,请参考以下文章

查找字符串中单词的 semordnilap(reverse anagram)

使用java在文本文件中查找字符串的问题

2021-10-16:单词拆分 II。给定一个非空字符串 s 和一个包含非空单词列表的字典 wordDict,在字符串中增加空格来构建一个句子,使得句子中所有的单词都在词典中。返回所有这些可能的句子。

C ++我不知道如何在字符串(句子)中找到一个单词(例如香蕉,三明治)用户输入句子然后写出那个单词

尝试使用数组在字符串中找到最短的句子

c语言如何实现在给定文档中查找想要的单词或句子,就好像word中一样,50分求解!