试着在星火中进行医生分类。我不确定散列在HashingTF中的作用是什么;它是否牺牲了任何准确性?我怀疑,但我不知道。火花科医生说它使用了“哈希技巧”..。这只是工程师使用的一个非常糟糕/令人困惑的命名的例子(我也是有罪的)。CountVectorizer还需要设置词汇表大小,但它有另一个参数,即一个阈值参数,可用于排除文本语料库中出现在某个阈值以下的单词或标记。我不明白这两台变形金刚之间的区别。使这一点重要的是算法中的后续步骤。例如,如果我想对生成的tfidf矩阵执行SVD,那么词汇表大小将决定SVD的矩阵大小,这会影响代码的运行时间和模型性能等。我很难在API文档和没有深度的实际琐碎示例中找到任何关于Spark Mllib的源。
发布于 2017-02-13 09:03:37
根据Spark2.1.0文档,
HashingTF和CountVectorizer都可以用来生成术语频率矢量。
HashingTF
HashingTF是一个转换器,它接受一组术语,并将这些集合转换成固定长度的特征向量。在文本处理中,“一组术语”可能是一袋单词。HashingTF利用哈希技巧。通过应用哈希函数将原始特性映射到索引(术语)中。这里使用的哈希函数是MurmurHash 3,然后根据映射的索引计算项的频率。这种方法避免了计算全局项到索引映射的需要,对于一个大型的语料库来说,这可能很昂贵,但是它会受到潜在的哈希冲突的影响,在散列之后,不同的原始特性可能成为相同的术语。 为了减少碰撞的可能性,可以增加目标特征维数,即哈希表的桶数。由于使用简单的模块将哈希函数转换为列索引,因此最好使用2的幂作为特征维,否则特性将不均匀地映射到列。默认的特性维度是2^18=262,144。可选的二进制切换参数控制术语频率计数。当设置为true时,所有非零频率计数都被设置为1。这对于离散概率模型中的二进制计数而不是整数计数特别有用。
CountVectorizer
CountVectorizer和CountVectorizerModel旨在帮助将文本文档集合转换为令牌计数向量。当先验字典不可用时,可以使用vocabulary,作为估计器提取并生成CountVectorizerModel。该模型通过词汇表为documents生成稀疏表示,然后可以传递给其他算法,如LDA。 在拟合过程中,CountVectorizer会在语料库中选择按词频顺序排列的顶级vocabSize单词。可选参数minDF还通过指定术语必须包含在词汇表中的文档的最小数量(或分数,如果< 1.0)来影响拟合过程。另一个可选的二进制切换参数控制输出向量。如果设置为true,则所有非零计数都设置为1。这对于离散概率模型中的二进制(而不是整数)计数特别有用。
示例代码
from pyspark.ml.feature import HashingTF, IDF, Tokenizer
from pyspark.ml.feature import CountVectorizer
sentenceData = spark.createDataFrame([
(0.0, "Hi I heard about Spark"),
(0.0, "I wish Java could use case classes"),
(1.0, "Logistic regression models are neat")],
["label", "sentence"])
tokenizer = Tokenizer(inputCol="sentence", outputCol="words")
wordsData = tokenizer.transform(sentenceData)
hashingTF = HashingTF(inputCol="words", outputCol="Features", numFeatures=100)
hashingTF_model = hashingTF.transform(wordsData)
print "Out of hashingTF function"
hashingTF_model.select('words',col('Features').alias('Features(vocab_size,[index],[tf])')).show(truncate=False)
# fit a CountVectorizerModel from the corpus.
cv = CountVectorizer(inputCol="words", outputCol="Features", vocabSize=20)
cv_model = cv.fit(wordsData)
cv_result = model.transform(wordsData)
print "Out of CountVectorizer function"
cv_result.select('words',col('Features').alias('Features(vocab_size,[index],[tf])')).show(truncate=False)
print "Vocabulary from CountVectorizerModel is \n" + str(cv_model.vocabulary)
输出如下所示:
散列TF错过了词汇,这是必不可少的技术,如LDA。为此,必须使用CountVectorizer函数。无论词汇量大小,CountVectorizer函数估计术语频率,而不涉及与HashingTF不同的任何近似。
参考资料:
https://spark.apache.org/docs/latest/ml-features.html#tf-idf
https://spark.apache.org/docs/latest/ml-features.html#countvectorizer
https://stackoverflow.com/questions/35205865
复制相似问题