def foo(self, n):
wordFreqDict = defaultdict(int)
resultList = []
for sentence in self.allSentences:
for word in self.wordSet:
if word in sentence:
wordFreqDict[word] += 1
for candidateWord in wordFreqDict:
if wordFreqDict[candidateWord] >= n:
resultList.append(candidateWord)
return resultList
我的函数基本上返回单词列表中的单词列表,如果它出现在至少n个句子中。我想要做的就是遍历self.allSentences是一个单词列表(句子)并迭代self.wordSet(语料库中的所有独特单词)并将每个单词的频率添加到字典中( wordFreqDict)。
然后遍历wordFreqDict并将一个频率为> = n的单词添加到resultList中。
我认为这会有效,但检查结果的时间太长。
有没有办法让它更有效率并缩短计算时间?
编辑:
以下是self.allSentences的计算方法
def storeAllSentences(self, corpus):
for sentence in corpus:
self.allSentences.append(sentence)
和self.wordSet:
def getUniqueWordSet(self, corpus):
for sentence in self.allSentences:
for word in sentence:
self.wordSet.append(word)
self.wordSet = set(self.wordSet)
答案 0 :(得分:1)
这里的假设是,如果一个单词唯一地出现在至少 n
个句子中,则会选择该单词。所以,即使它在一个句子中出现10次,那仍然是一次。
一些明显的问题是您的嵌套循环和in
检查字符串。这实际上是复杂的立方体。应该可以使用set
+ Counter
来大幅减少这种情况。
from collections import Counter
from itertools import takewhile
def foo(self, n):
c = Counter()
for sent in self.allSentences:
c.update(set(sent))
resultSet = list(itertools.takewhile(lambda x: x[1] >= n, c.most_common()))
return resultSet
在这里,我使用正则表达式删除特殊字符和标点符号,然后我拆分并检索句子中的所有唯一单词。然后更新Counter
。
最后,使用itertools.takewhile
提取所需频率(或更多)的所有单词并返回。
如果sent
是一个字符串句子,您可以使用基于re
的过滤来删除标点符号,然后拆分:
import re
tempWordSet = set(re.sub('[^\w\s]+', '', sent).split())
c.update(tempWordSet)
这不考虑单词是否属于self.wordSet
。因此,如果您也想要这样,您可以稍微修改第一个循环以包含filter
步骤:
c.update(set(filter(lambda x: x in self.wordSet, sent)))
或者,使用第二种技术:
tempWordSet = set(filter(lambda x: x in self.wordSet,
re.sub('[^\w\s]+', '', sent).split()))
在一个不相关的说明中,您是否尝试执行文本挖掘?您可能有兴趣研究TFIDF。
答案 1 :(得分:1)
集合 wordSet 可能比单个句子中的单词大至少两个数量级。因此,它通过句子中的单词循环有意义。但是,这要求拆分句子并不是一个非常慢的操作。如果是,则应该在getUniqueWordSet中执行整个过程。这里只改变了第一个for循环:
def foo(self, n):
wordFreqDict = defaultdict(int)
resultList = []
for sentence in self.allSentences:
for word in sentence:
# This if may be left out if allSentences is guaranteed to stay the same after storing them
if word in self.wordSet:
wordFreqDict[word] += 1
for candidateWord in wordFreqDict:
if wordFreqDict[candidateWord] >= n:
resultList.append(candidateWord)
return resultList