自然语言处理(NLP)基础概念(一):词向量(word vector)及其生成方法介绍

自然语言处理(NLP)基础概念(一):词向量(word vector)及其生成方法介绍

该文章是系列文章“利用深度学习进行自然语言处理( Natural Language Processing with Deep Learning)”的第一部分。

该系列文章主要是2017年斯坦福大学CS224n课程的学习笔记。

课程地址:CS224n: Natural Language Processing with Deep Learning

=================================================================

1. 自然语言处理介绍 Introduction to Natural Language Processing

1.1 NLP有什么特别之处

人类语言是一套用来传达含义的系统,不由任何形式的身体行为( a physical manifestation)产生,所以它和其他一些机器学期任务非常不同。

大部分的单词只是一种符号而已,例如 "rocket"代表火箭的概念,也可以扩展为一个火箭。当我们用 "Whooompaa"来表达含义时,这个符号可以被编码为多种形式,例如声音,手势等等的连续信号,因为 "Whooompaa"可能表示的含义超过单词本身,更多的是一种强烈的情绪。

1.2 一些自然语言处理任务的例子

自然语言处理的目标是使机器能够理解自然语言,从而执行一些任务。这些任务按照难度有不同的等级

简单任务:

  • 拼写检查(Spell Checking)
  • 关键字搜索(Keyword Search)
  • 寻找同义词(Finding Synonyms)

中级任务:

  • 从网页和文档解析信息(Parsing information from websites, documents, etc.)

复杂任务:

  • 机器翻译(Machine Translation )
  • 语义分析(Semantic Analysis)
  • 指代分析(Coreference)例如,"he" 和 "it" 在文档中指谁或什么?
  • 问答系统(Question Answering)

1.3 怎么表示单词

怎么表示单词是自然语言处理的最基本问题。

词向量(word vectors)能够将单词与单词间的相似性和差异性编码进词向量,方法是利用距离测量方法如Jaccard, Cosine, Eu-clidean。

2. 词向量(Word Vectors)

英语大概有约1300万单词。词向量就是将单词映射到词空间的一个点。

注意,词向量在英文里有两个可以互相替换使用的说法: word embeddings和word vectors

为什么利用词向量?一个最直观的原因是,我们可以找到一个N维(N小于1300万)的空间,足够编码我们所有的单词。

每一个维度可以编码一些意思,例如语义空间可以编码时态、单复数和性别。

one-hot向量(one-hot vector):

one-hot向量就是利用一个 R^{|V|\times1} 向量来表示单词。

|V|是词汇表中单词的数量。

一个单词在英文词汇表中的索引位置是多少,那么相对应的那一行元素就是1,其他元素都是0。

下面是一个例子,‘Aardvark’这个单词常排在高阶英语词典的第一位,因此‘Aardvark’的词向量就表示为:

w^{Aardvark}=\begin{vmatrix} 1 \\0 \\0 \\\vdots \\0 \end{vmatrix}

再举一个例子:'zebra'这个单词在英文词汇表中排最后一位,所以它的词向量可以表示为:

w^{zebra}=\begin{vmatrix} 0 \\0 \\0 \\\vdots \\1 \end{vmatrix}

one-hot向量表示词向量的缺点是,由于每一个单词都有一个独立的词向量表示,这样无法体现出单词间的相似度,例如单词motel和hotel有一定的相似度,那么这两个单词的词向量的乘积应该不等于0,但是:

(w^{hotel})^Tw^{motel} = 0

因此我们应该减少词空间的大小 |V|,找到一个合适大小的子空间表示词向量。

下面介绍一些生成词向量的方法,主要有两类:矩阵奇异值分解方法(SVD)和基于迭代的方法(Word2vec)

3. 矩阵奇异值分解方法(SVD Based Methods)

SVD( Singular Value Decomposition)矩阵奇异值分解。

首先我们在一个语料库中累积计算单词同时出现的次数,形成某种形式的矩阵X(形成哪种形式后面会讲)。

对X进行SVD,得到 USV^T ,就可以用U的行来表示词向量了。

下面说一说一些可选的矩阵X。

3.1 词-文档矩阵(Word-Document Matrix)

首先假设相似度较高的单词非常有可能出现在同一个文档中。

遍历数以百万的文档,当第i个单词出现在第j个文档中时,我们给 X_{ij} 增加1。

当然,这会形成一个巨大的矩阵,所以我们可恶意尝试一下其他的矩阵X。

3.2 基于窗口的共生矩阵(Window based Co-occurrence Matrix)

基于窗口的共生矩阵就是在词-文档矩阵的基础上,设定一个我们感兴趣的单词数量作为窗口大小,使矩阵不至于太大。

例如,假设我们的语料库只有三个句子,如下:

1. I enjoy flying.

2. I like NLP.

3. I like deep learning.

那么生成的共生矩阵如下:

3.3 对共生矩阵进行矩阵奇异值分解(Applying SVD to the cooccurrence matrix)

  • 生成 |V| × |V|共生矩阵X
  • 对共生矩阵进行矩阵奇异值分解得到 USV^T


  • 选择U的前k列作为k维词空间


  • 如何确定k,计算 \frac{\sum_{i=1}^{k}{\sigma_i}}{{\sum_{i=1}^{|V|}{\sigma_i}}} (代表前k个 \sigma (方差)占全部的比值,一般很少一部分即可代表全部),然后选定合适的k。
  • 那么 U_{1:|V|,1:k} 就是我们的k维词向量

矩阵奇异值分解方法方法存在的问题:

  • 矩阵的维度经常变化(新单词加入频繁引起语料库的规模变化)。
  • 矩阵稀疏性太大,因为大多数单词不是同时出现的。
  • 矩阵维度太大。
  • 训练成本太大(例如应用SVD时)。
  • 需要对X矩阵进行大量处理来避免单词频率的过大差异。

解决方法:

  • 忽略一些功能性单词,如 "the", "he", "has"等等。
  • 给窗口加权重
  • 用Pearson correlation将0次计数记为负数

下面即将要讲的方法 “Word2vec—基于迭代的方法(iteration based methods)”可以用更优雅的方式解决上述问题。

4. Word2vec—基于迭代的方法(iteration based methods)

接下来的内容我们要介绍两个 Word2vec算法:Skip-grams(SG)算法和连续袋算法(Continuous Bag of Words)一般简写为CBOW。

1. Skip-grams (SG)算法
给出目标单词,预测它的上下文单词。

以下图为例:

图中的love是目标单词,其他是上下文单词,那么我们就是求 P(w_{you}|w_{love})P(w_{Do}|w_{love})P(w_{deep}|w_{love})P(w_{learning}|w_{love})

2. Continuous Bag of Words (CBOW)连续袋算法

给出上下文单词,预测目标单词。

以下图为例:

我们求的是 P(w_{love}|w_{do}) 等等。

另外本部分内容还要介绍两种模型训练方法:

  1. 分层softmax(Hierarchical softmax)
  2. 负采样(Negative sampling)

下面开始详细介绍,再次之前,先让我们来了解以下语言模型。

4.1 语言模型 Language Models (Unigrams, Bigrams, etc.)

Unigram model:

以一个英文句子为例: "The cat jumped over the puddle."
模型的目的就是给这个句子一个概率值P,用 W_i 代表句子中的单词,那么一个有n个单词的句子的概率可以表示为:

P(w_1,w_2,\cdots,w_n) = \prod_{i=1}^{n}P(w_i)

这儿就是Unigram model。

Bigram model:

但是Unigram model假设每一个单词都是独立的,这并不合理!

如果我们假设每一个单词都与它的前一个单词有关,那么P是下面这种形式:

P(w_1,w_2,\cdots,w_n)=\prod_{i=2}^{n}P(w_i|w_i-1)

这就是Bigram model。

理解了Unigrams, Bigrams模型就可以继续往下进行了,下面介绍一些模型用来得到上述这些概率。

4.2 连续袋模型 Continuous Bag of Words Model (CBOW)

以下面这个句子为例: {"The", "cat", ’over", "the’, "puddle"}。

模型能够从例句中预测中间缺少一个单词“jump”,那么这种模型我们就成为连续袋模型。

首先我们创建两个矩阵: U\in R^{|V|\times{n}}V \in R^{n\times |V|} 。V是输入矩阵,U是输出矩阵。n是输入的单词数量,|V|是词汇表的维度。

w_i 表示词汇表V中的第i个单词。

\nu_i 表示V的第i列向量,也就是代表输入单词 w_i 的词向量。

\mu_i 表示U的第i行向量,也就是代表输出单词 w_i 的词向量。

下面介绍连续袋模型的流程:

  1. 将输入句子中的单词生成one-hot词向量(本文第二部分介绍过什么是one-hot词向量): \left( x^{c-m},\dots,x^{c-1},x^{c+1},\dots,x^{c+m} \in R^{|V|} \right)
  2. 通过将one-hot词向量和输入矩阵V相乘,得到输入单词的词向量: \nu_{c-m} = Vx^{c-m}, \nu_{c-m+1}=Vx^{c-m+1},\dots,\nu_{c+m}=Vx^{c+m}
  3. 对上述词向量求平均得到: \bar{\nu} = \frac{\nu_{c-m}+\nu_{c-m+1}+\dots+\nu_{c+m}}{2m} \in R^n
  4. 上面的平均词向量与输出矩阵进行点乘运算,得到得分向量(score vector) z = U\bar{\nu} \in R^{|V|} ,我们知道,两个向量约相似,点乘得到的分数越高,因此将会使相似的词互相靠近,从而得到较高的分数。
  5. 将分数转换成概率 \bar {y} = softmax(z) \in R^{|V|} 。'softmax'就是对 \bar {y} 做如下运算 \frac{e^{\bar{y_i}}}{\sum_{k=1}^{|V|}{e^{\bar{y_k}}}} ,使其每一个元素在[0,1]范围内,且和为1。
  6. 我们希望 \bar y 与真实的 y 匹配,也就是真实的 y 的one-hot向量。

上面步骤说明了在有矩阵 UV 的情况下,连续袋模型是如何工作的,下面介绍一下如何产生这两个矩阵:

首先,为了计算预测值的准确性,我们先定义一个测量函数,这里,我们选择一个非常流行的测量函数:交叉熵(cross entropy) H(\bar{y},y)

H(\bar{y},y) = - \sum_{j=1}^{|V|}{y_jlog{\bar{y_j}}}

由于y是one-hot向量,所以上面的公式可以简化为:

H(\bar{y},y) = -{y_jlog{\bar{y_j}}}

让我们举例说明这个公式:

假设我们的预测是完美的,也就是说 \bar {y_c}=1,那么H(yˆ, y) =
−1 log(1) = 0。损失函数为0,也就意味着没有任何‘惩罚’,也就是不需要更新我们的矩阵 UV

假设我们的预测非常糟糕,假设 \bar{y_c} =0.01,那么 H = -1log(0.01) \approx4.6.5 ,这个值比较大,说明损失较大,需要“惩罚“。

也就是说,为了评估我们的预测结果的好坏,连续袋模型(CBOW)定义了一个代价(cost),为了最优化这个代价,我们需要对矩阵 UV 进行升级,采用的升级方法就是随机梯度下降(stochastic gradient descent)。

P(w_c|w_{c-m},w_{c-m+1},\dots,w_{c+m-1},w_{c+m}) 最大,根据上面的公式,也就是使 J 最小。


4.3 Skip-Gram模型 (Skip-Gram Model)

Skip-Gram模型与连续袋模型正好相反。

连续袋模型是根据周围的词来预测中心的词,而Skip-Gram模型是根据中心的词预测周围的词。

4.4 负采样 Negative Sampling

4.5 Hierarchical Softmax

编辑于 2017-09-21