Word2vec模型
1. 词的表示
1.1 能指与所指
一个词(如 tea
)是一个符号/能指 (Signifier),它代表了现实或想象世界中的某个实体/所指 (Signified)。词义是极其复杂的,它源于人类在世界中沟通和实现目标的意图。
1.2 离散词表示:One-Hot 向量
最简单的表示方法是将每个词视为独立的实体。在向量空间中,这通常通过 one-hot 向量(或称标准基向量) 来实现。
例如,在一个词汇表 V 中:
vtea=[0,0,1,0,…,0]T vcoffee=[0,0,0,0,…,1,…,0]T这种表示方法的缺陷在于,它无法表达词与词之间的相似性关系。任意两个不同词的one-hot向量的点积都为0,意味着在模型看来,所有词都同等地“不相似”。
2.3 基于人工标注属性的向量
另一种方法是根据语言学资源(如WordNet)手动为词语标注各种属性(如同义词、上下位词、语法信息等),然后构建特征向量。
例如,v_tea
可能包含 [is_plural: 0, is_beverage: 1, ..., is_synonym_of_chai: 1]
等特征。
3. 分布式语义与 Word2vec
3.1 分布式假设
"You shall know a word by the company it keeps." — J. R. Firth
这是现代NLP中最具影响力的思想之一:一个词的意义可以由其上下文(Context) 中出现的词的分布来定义。与 tea
相似的词(如 coffee
)倾向于出现在相似的上下文中。
3.2 共现矩阵
基于分布式假设,我们可以构建一个 共现矩阵 X。X 的大小为 ∣V∣×∣V∣,其中 Xij 表示词 i 和词 j 在同一上下文(如一个窗口或一篇文档)中出现的次数。
- 短窗口 (e.g., 2-5 words): 倾向于捕捉句法 (Syntactic) 信息。
- 长窗口 (e.g., document-level): 倾向于捕捉语义 (Semantic) 或 主题 (Topic) 信息。
这种方法的问题在于,生成的向量维度过高(等于词汇表大小),并且原始计数对高频词(如 the
)的权重过高。
3.3 Word2vec 模型与目标函数
Word2vec 是一种从数据中学习词的低维稠密向量(Embedding) 的模型。这里我们介绍 Skip-gram 算法。
a. 模型定义
给定一个中心词 c (center word),模型的目标是预测其上下文中的一个外部词 o (outside word)。模型为词汇表 V 中的每个词 w 学习两个向量:
- vw:当 w 作为中心词时的向量。
- uw:当 w 作为外部词时的向量。
模型使用 softmax 函数定义条件概率 p(o∣c):
p(o∣c)=∑w∈Vexp(uwTvc)exp(uoTvc)我们通过最小化与真实分布 P∗(O∣C) 的交叉熵损失目标来估计参数 U,V 的取值:
U,VminEo,c[−logpU,V(o∣c)]交叉熵损失:交叉熵损失分为分类交叉熵和二元交叉熵。 对于分类交叉熵,其计算公式如下:
J=−j=1∑Cyj⋅log(y^j)其中:
C 是类别的总数。
yj 是真实标签 one-hot 向量的第 j 个元素(值为 0 或 1)。
y^j 是模型预测的第 j 个类别的概率。
log 通常是自然对数(ln)。
对于二元交叉熵,其计算公式如下:
J=−[y⋅log(y^)+(1−y)⋅log(1−y^)]其中:
y 是真实标签(0 或 1)。
y^ 是模型预测样本为正类(y=1)的概率。
1−y^ 是模型预测样本为负类(y=0)的概率。
b. 目标函数
我们的目标是最大化给定中心词时,预测真实上下文词的概率。这等价于最小化负对数似然 (Negative Log Likelihood):
J(θ)=−T1t=1∑Tj∈context(t),j=0∑logp(wt+j∣wt)我们通过梯度下降 (Gradient Descent)等优化算法来调整参数 U 和 V,以最小化该损失函数。
3.3 从语料库中训练word2vec模型
a. 经验损失函数
设:
- D 为文档集合 d,每个文档是单词序列 w1(d),…,wm(d),w∈V。
- k∈N++ 为正整数窗口大小。
我们来定义中心词随机变量 C 和外部词随机变量 O 如何与这个具体数据集对应。O 取每个文档中每个单词 wi 的值,对于每个 wi,其外部词为 wi−k,…,wi−1,wi+1,…,wi+k。因此,我们的目标函数变为:
L(U,V)=d∈D∑i=1∑mj=1∑k−logpU,V(wi−j(d)∣wi(d))这个式子的意义是:对所有文档、文档中所有单词、窗口内所有外部词,计算外部词在中心词条件下的似然的和。
b.梯度方法
我们通过梯度方法来寻找较优的 U 和 V,以优化我们设定的目标函数:我们从一个相对随机的初始猜测出发,反复沿着能在局部最优地改进目标的方向调整参数。这就是梯度法。
标量函数 f 关于参数矩阵 U 的梯度(记作 ∇Uf),表示在局部上让 f 增大的 U 的变化方向。
实际操作中,我们通常将 U(0) 和 V(0) 随机初始化为 U,V∼N(0,0.001)∣V∣×d(即每个元素独立采样自均值为0、方差很小的正态分布),然后进行如下迭代:
U(i+1)=U(i)−α∇UL(U(i),V(i))
这表示在第 i+1 次迭代时,U 的值等于上一次的值减去一个小步长 α 乘以梯度,从而在目标 L(U,V) 上取得局部最优的改进。
这里的 α 也是学习率。
c. 梯度具体计算与含义
我们首先写出梯度,并将梯度算子传递到求和符号内:
∇vcL^(U,V)=d∈D∑i=1∑mj=1∑k−∇vclogpU,V(wi−j(d)∣wi(d))这些项的梯度就是它们各自梯度的和。我们将 wi−j(d) 记为 o,wi(d) 记为 c,只考虑一项:
∇vclogpU,V(o∣c)=∇vclog∑w=1nexp(uw⊤vc)exp(uo⊤vc)=∇vclogexp(uo⊤vc)−∇vclogw=1∑nexp(uw⊤vc)而:
∇vclogexp(uo⊤vc)=uo将点乘展开,然后对 vc 求偏导即可。最终结果即为 uo。
−∇vclogw=1∑nexp(uw⊤vc)=x=1∑npU,V(x∣c)ux综上可得:
uo−x=1∑npU,V(x∣c)ux=uo−E[ux]也就是“观测到的”减去“期望的”。直观上,vc 向量会被更新得更像实际观测到的词向量 uo,而不是模型期望的词向量。
“更像实际观测到的词向量 uo”:这是由梯度的 +uo 部分决定的。更新的目标是让 vc 向 uo 靠拢。 “而不是模型期望的词向量”:这是由梯度的 −E[ux] 部分决定的。更新的过程不是简单地加强模型现有的期望,而是要减去这个期望的影响,从而为“事实” uo 留出空间。
3.4 Skip-gram 负采样
在 Skip-gram 模型中,计算 p(o∣c) 的分母(归一化项)非常耗时,因为它需要对词汇表中的所有词进行计算。
对此,我们尝试从另一个角度来理解归一化操作的意义。我们先重写 softmax 公式:
pU,V(o∣c)=∑w∈Vexp(uw⊤vc)exp(uo⊤vc)
其中,分子 exp(uo⊤vc) 表示词 c 与上下文 o 的关联度,分母 ∑w∈Vexp(uw⊤vc) 是分区函数(归一化项)。
从概率的角度看,分区函数保证所有概率之和为 1(指数函数保证分数非负)。而从学习的角度看,分区函数会 “压低”所有非观测词的分数。换句话说,分子鼓励模型让 uo 更像 vc,而分母则让所有 w=o 的 uw 更不像 vc。
负采样(negative sampling)的直觉是:我们没必要每次都压低所有 uw,因为这会带来很大的计算开销。相反,我们可以提出下面的新的策略:对于每个 (中心词, 上下文词)
正样本对,我们不再更新整个词汇表的权重,而是随机抽取 k 个负样本(即不太可能出现在上下文中的词)。
SGNS 的目标函数为:
J(θ)=logσ(uoTvc)+i=1∑kEwi∼Pn(w)[logσ(−uwiTvc)]其中:
σ(x)=(1+e−x)1- 第一项最大化观察到的 (c,o) 对的概率。
- 第二项最小化随机采样的负样本 (c,wi) 的概率。
σ 函数将可以是任意实数的“相似度分数”压缩到 (0, 1) 区间内。这个输出值就可以被解释为“o真的是c的上下文”这件事的概率。
σ 函数有个非常优美的性质:1−σ(x)=σ(−x),可以很方便的表示负样本的概率。
这种方法将一个复杂的多分类问题转化为了多个简单的二分类问题,极大地提升了训练效率,同时保证了词向量的质量。