特征工程-2-文本表示模型
4 文本表示模型
TF-IDF
TF-IDF(term frequency–inverse document frequency)是一种用于信息检索与数据挖掘的常用加权技术,常用于挖掘文章中的关键词,而且算法简单高效,常被工业用于最开始的文本数据清洗。
TF-IDF有两层意思,一层是"词频"(Term Frequency,缩写为TF),另一层是"逆文档频率"(Inverse Document Frequency,缩写为IDF)。其公式为:
其中\(TF(t,d)\)为单词t在文档d中出现的频率,\(IDF(t)\)是逆文档频率,用来衡量单词t对其表达语义所起的重要性,表示为:
加1平滑,防止单词 t 未再文章中出现
如果一个单词在非常多的文章里面都出现,那么它可能是一个比较通用的词汇,对于区分某篇文章特殊语义的贡献较小,因此对权重做一定惩罚。
from sklearn.feature_extraction.text import TfidfVectorizer
corpus = [
'This is the first document.',
'This document is the second document.',
'And this is the third one.',
'Is this the first document?',
]
vectorizer = TfidfVectorizer()
X = vectorizer.fit_transform(corpus)
vectorizer.get_feature_names_out()
print(X.shape)
词袋模型
词袋模型(bag-of-words)将每篇文章看成一袋子词,并忽略每个词出现的顺序。模型将整段文本以词为单位切分开,然后每篇文章可以表示成一个长向量,向量中的每一维代表一个单词,而该维对应的权重则反映了这个词在原文章中的重要程度。
from sklearn.feature_extraction.text import CountVectorizer
corpus = [
'This is the first document.',
'This document is the second document.',
'And this is the third one.',
'Is this the first document?',
]
vectorizer = CountVectorizer()
X = vectorizer.fit_transform(corpus)
vectorizer.get_feature_names_out()
print(X.toarray())
# [[0 1 1 1 0 0 1 0 1]
# [0 2 0 1 0 1 1 0 1]
# [1 0 0 1 1 0 1 1 1]
# [0 1 1 1 0 0 1 0 1]]
vectorizer2 = CountVectorizer(analyzer='word', ngram_range=(2, 2))
X2 = vectorizer2.fit_transform(corpus)
print(vectorizer2.get_feature_names_out())
# array(['and this', 'document is', 'first document', 'is the', 'is this',
# 'second document', 'the first', 'the second', 'the third', 'third one',
# 'this document', 'this is', 'this the'], ...)
print(X2.toarray())
# [[0 0 1 1 0 0 1 0 0 0 0 1 0]
# [0 1 0 1 0 1 0 1 0 0 1 0 0]
# [1 0 0 1 0 0 0 0 1 1 0 1 0]
# [0 0 1 0 1 0 1 0 0 0 0 0 1]]
可能会出现的问题:长文本比短文本对每个单词有更高的出现次数,尽管他们可能在描述同一个主题,用单词计数会有偏差。
其改进方法:
- 去停用词:可去掉一些无用的高频词
- 可以使用TF-IDF来计算权重,请查考TF-IDF章节
n-gram模型
n 元词袋(bag-of-n-grams)是词袋的一种自然扩展,n-gram(n元词)是由n个标记(token)组成的序列。1-gram 就是一个单词(word),又称为一元词(unigram)。经过分词(tokenization)之后,计数机制会将单独标记转换为单词计数,或将有重叠的序列作为 n-gram 进行计数。n-gram 能够更多地保留文本的初始序列结构,因此 n 元词袋表示法可以表达更丰富的信息。
理论上,有k个不同的单词,就会有 \(k^2\) 个不同的 2-gram(二元词),实际上,没有这么多,因为并不是每个单词都可以跟在另一个单词后面。n-gram(n > 1)一般来说也会比单词多得多,这意味着 n 元词袋是一个更大也更稀疏的特征空间,也意味着 n 元词袋需要更强的计算、存储、建模能力。n 越大,能表示的信息越丰富,相应的成本也会越高。
另外,同一个词可能有多种词性变化,却具有相似的含义。在实际应用中,一般会对单词进行词干抽取(Word Stemming)处理,即将不同词性的单词统一成为同一词干的形式。
主题模型(topic model)
基于词袋模型或N-gram模型的文本表示模型有一个明显的缺陷,就是无法识别出两个不同的词或词组具有相同的主题。因此,需要一种技术能够将具有相同主题的词或词组映射到同一维度上去,于是产生了主题模型。主题模型通过将高维单词空间映射到低维的目标主题空间,有效地发现文档潜在的结构和隐藏的语义信息,最终实现对目标文档的降维处理、信息总结和摘要。
主题模型是一种特殊的概率图模型。主题模型自动分析每个文档,统计文档内的词语,根据统计的信息来断定当前文档含有哪些主题,以及每个主题所占的比例各为多少。
-
pLAS(Probabilistic Latent Semantic Analysis)
Hofmann 等 人提出概率潜在语义分析(Probabilistic Latent Semantic Analysis, PLSA)模型,在该模型中不考虑词序,文本语料可以由单词和文档地共现矩阵表示。
从观测的单词中推断两个参数:一个是将语料库中文档联系起来的全局参数,代表了给定主题后,单词出现的概率;另一个是每篇文档的参数, 代表了文档的主题概率分布。PLSA 模型通过引入 概率统计思想,大大降低了模型的计算成本。
pLSA是用一个生成模型来建模文章的生成过程。假设有K个主题,M篇文章;对语料库中的任意文章d,假设该文章有N个词,则对于其中的每一个词,我们首先选择一个主题z,然后在当前主题的基础上生成一个词w。如下图模型:
生成主题 \(z\) 和词 \(w\) 的过程遵照一个确定的概率分布。
设在文章 \(d\) 中生成主题 \(z\) 的概率为 \(p(z|d)\),在选定主题的条件下生成词 \(w\) 的概率为\(p(w|z)\),则给定文章 \(d\) ,生成词 \(w\) 的概率可以写成:\(p(w \mid d)=\sum_{z} p(w \mid z, d)\ p(z \mid d)\)。
在这里我们做一个简化,假设给定主题 \(z\) 的条件下,生成词 \(w\) 的概率是与特定的文章无关的,则公式可以简化为:\(p(w \mid d)=\sum_{z} p(w \mid z) p(z \mid d)\)。整个语料库中的文本生成概率可以用似然函数表示为:
\[L=\prod_{m}^{M} \prod_{n}^{N} p\left(d_{m}, w_{n}\right)^{c\left(d_{m}, w_{n}\right)} \]其中 \(p(d_m,w_n)\) 是在第 \(m\) 篇文章 \(d_m\) 中,出现单词 \(w_n\) 的概率,\(c(d_m,w_n)\) 是在第 \(m\) 篇文章 \(d_m\) 中,单词 \(w_n\)出现的次数。
于是,\(\log\) 似然函数可以写成:
\[\begin{aligned} l &=\sum_{m}^{M} \sum_{n}^{N} c\left(d_{m}, w_{n}\right) \log p\left(d_{m}, w_{n}\right) \\ &=\sum_{m}^{M} \sum_{n}^{N} c\left(d_{m}, w_{n}\right) \log \sum_{k}^{K} p\left(d_{m}\right) p\left(z_{k} \mid d_{m}\right) p\left(w_{n} \mid z_{k}\right) . \end{aligned} \]其中,定义在文章上的主题分布 \(p(z_k|d_m)\) 和定义在主题上的词分布 \(p(w_n|z_k)\) 是待估计的参数。由于参数中包含的zk是隐含变量,可以利用最大期望算法来解决。
在 PLSA 模型中,对特定文档中的主题的混合比例权重没有做任何假设,因此,在实际训练时常出现 过拟合的情况。
-
LDA(Latent Dirichlet Allocation)
LDA可以看作是pLSA的贝叶斯版本,其文本生成过程与pLSA基本相同,不同的是为主题分布和词分布分别加了两个狄利克雷(Dirichlet)先验。模型结构如下:
- 其中,方框表示对其中内容的重复次数,方框右下角数字是方框内包含变量的重复次数;棕色实心圆表示观测值,空心圆表示隐含随机变量;箭头表示变量的依赖关系;变量之间的指代关系如下表所示:
符号 解释 符号 解释 K 主题个数 M 文档个数 N 表示文档包含的单词个数 W(\(W_{dn}\)) 表示第 d 篇文档的第 n 个单词 Z (\(Z_{dn}\)) 表示第 d 篇文档的第 n 个主题 \(\theta / \varphi\) 超参数不同的狄利克雷概率分布 语料库的生成过程为:
假设一个语料库是 D 篇文档集合;其中,每篇文档 d 是 N 个单词的序列,表示为 \(W = [w_1,w_2, ..., W_n]\),对语料库 D 中的每一篇文档 \(d_i\),采用以下操作:
- 从超参数为 \(\alpha\) 的狄利克雷分布中抽样生成文档 \(d_i\) 的主题分布 \(\theta_i\)
- 对文档 \(d_i\) 中的每一个词进行以下3个操作:
- 从代表主题的多项式分布 \(\theta_i\) 中抽样生成它所对应的主题 \(z_{ij}\)
- 从超参数为 \(\beta\) 的狄利克雷分布中抽样生成主题 \(z_{ij}\) 对应的词分布 \(\psi_{z_{ij}}\)
- 从代表词的多项式分布 \(\psi_{z_{ij}}\) 中抽样生成词 \(w_{ij}\)
首先随机给定每个单词的主题,然后在其他变量固定的情况下,根据转移概率抽样生成每个单词的新主题。
对于每个单词来说,转移概率可以理解为:给定文章中的所有单词以及除自身以外其他所有单词的主题,在此条件下该单词对应为各个新主题的概率。
最后,经过反复迭代,我们可以根据收敛后的采样结果计算主题分布和词分布的期望
在LDA中,主题的个数 K 是一个预先指定的超参数。对于模型超参数的选择,实践中的做法一般是将全部数据集分成训练集、验证集、和测试集3部分,然后利用验证集对超参数进行选择。
在训练时,尝试多组超参数的取值,并在验证集上检验哪一组超参数所对应的模型取得了最好的效果。最终,在验证集上效果最好的一组超参数和其对应的模型将被选定,并在测试集上进行测试。为了衡量LDA模型在验证集和测试集上的效果,需要寻找一个合适的评估指标。一个常用的评估指标是困惑度(perplexity)。在文档集合 D 上,模型的困惑度被定义为:
\[\operatorname{perplexity}(D)=\exp \left\{-\frac{\sum_{d=1}^{M} \log p\left(\boldsymbol{w}_{d}\right)}{\sum_{d=1}^{M} N_{d}}\right\} \]其中 M 为文档的总数,\(w_d\)为文档 d 中单词所组成的词袋向量,\(p(w_d)\) 为模型所预测的文档 d 的生成概率,\(N_d\) 为文档 d 中单词的总数。
词嵌入模型(word embeding)
词嵌入是一类将词向量化的模型的统称,核心思想是将每个词都映射成低维空间(通常K=50~300维)上的一个稠密向量(Dense Vector)。K维空间的每一维也可以看作一个隐含的主题,只不过不像主题模型中的主题那样直观。
下一篇模型将详细讲解一下词嵌入模型。