大数据的TFIDF

2024-04-24 17:14:57 发布

您现在位置:Python中文网/ 问答频道 /正文


Tags: python
3条回答

我相信你可以用一个HashingVectorizer从你的文本数据中得到一个很小的csr_matrix,然后用一个TfidfTransformer在上面。存储一个由800万行和数万列组成的稀疏矩阵并不是什么大事。另一个选择是完全不使用TF-IDF——这可能是您的系统在没有它的情况下工作得相当好的情况。

在实践中,您可能需要对数据集进行子采样—有时系统也会通过从所有可用数据的10%中进行学习而达到同样的效果。这是一个经验问题,没有办法提前告诉你什么策略最适合你的任务。在我确信我需要它们之前,我不会担心扩展到800万个文档(也就是说,直到我看到一条学习曲线显示出明显的上升趋势)。

下面是我今天早上做的一个例子。您可以看到,随着我添加更多文档,系统的性能趋于提高,但它已经处于一个似乎没有什么影响的阶段。考虑到训练要花多长时间,我认为用500份文件来训练不值得我花时间。

我用sklearn和pandas来解决这个问题。

使用pandasiterator在数据集中迭代一次,并创建一组所有单词,然后在countvector词汇表中使用它。这样,计数矢量器将生成一个稀疏矩阵列表,所有这些矩阵都具有相同的形状。现在使用vstack对它们进行分组。得到的稀疏矩阵与CountVectorizer对象具有相同的信息(但单词顺序不同),并且与所有数据都匹配。

如果考虑到时间复杂性,这个解决方案不是最好的,但对内存复杂性是有好处的。我在20GB+的数据集中使用它

我编写了一个python代码(不是完整的解决方案),它显示属性、编写生成器或使用pandas块在数据集中进行迭代。

from sklearn.feature_extraction.text import CountVectorizer
from scipy.sparse import vstack


# each string is a sample
text_test = [
    'good people beauty wrong',
    'wrong smile people wrong',
    'idea beauty good good',
]

# scikit-learn basic usage

vectorizer = CountVectorizer()

result1 = vectorizer.fit_transform(text_test)
print(vectorizer.inverse_transform(result1))
print(f"First approach:\n {result1}")

# Another solution is

vocabulary = set()

for text in text_test:
    for word in text.split():
        vocabulary.add(word)

vectorizer = CountVectorizer(vocabulary=vocabulary)

outputs = [] 
for text in text_test: # use a generator
    outputs.append(vectorizer.fit_transform([text]))


result2 = vstack(outputs)
print(vectorizer.inverse_transform(result2))

print(f"Second approach:\n {result2}")

最后,使用TfidfTransformer

Gensim有一个高效的tf-idf model,不需要一下子把所有东西都放在内存中。

你的语料库只需要是一个iterable,所以它不需要一次记住整个语料库。

根据评论,这款{a2}在一台笔记本电脑上运行了大约50万次,覆盖了维基百科。

相关问题 更多 >