分享

Word2vec, Fasttext, Glove, Elmo, Bert, Flair训练词向量教...

 520jefferson 2020-08-12

一、word2vec

1、genism库

gensim库中提供了word2vec的cbow模型和skipgram模型的实现,可直接调用

完整版参考代码

2、tensorflow实现skipgram模型

skipgram模型使用中心词预测上下文,网上介绍很多了也可直接去看论文

本模型实验采用的数据时wiki百科中文数据,有原版和分词后版本,数据量大下载请移步Github,实现详细直接看代码,代码中关键处都有注释,这里提一下word2vec中常用的nce loss损失函数,nce loss函数个参数定义如下:

解释一下参数sampled_values,从tensorflow的nce_loss源代码中可以看到当sampled_ values=None时采样方式,word2vec中负采样过程其实就是优选采样词频高的词作负样本

在上图中展现了nce_loss在实际使用过程中参数列表以及各个参数的含义,下面我们看一下tensorflow源码中对于nce_loss函数的实现逻辑:

Tensorflow实现skipgram模型完整细节参考代码,训练测试效果可参见下图:


二、fasttext中文词向量训练 

1、fasttext词向量实战简介

facebook在github上发布了fasttext用于文本分类和词向量训练的官方代码,可直接用于中文词向量训练,下载网址是:

https://github.com/facebookresearch/fastText

下载下来之后首先需要make编译一下,编译通过之后便可直接使用如下命令进行中文词向量训练,也可对参数进行调节:

$./fasttext skipgram -input data/fil9 -output result/fil9

上面命令是使用skipgram进行词向量学习,当然也可以使用cbow进行词向量学习:

$./fasttext cbow -input data/fil9 -output result/fil9

可调参数有:词向量的维度、subwords范围、epoch、learning_rate、thread

$./fasttext skipgram -input data/fil9 -output result/fil9 -minn 2 -maxn 5

-dim100 –epoch 2 –lr 0.5 –thread 4

同时可以用训练出来的词向量模型进行词向量打印和临近词向量查询等操作,自然在用命

令进行训练前需要准备好数据,即准备好中文分词或是分字的文本数据作为数据

fasttext详细词向量训练过程以及各参数含义请移步博文,此文中都有详细的介绍:

https://blog.csdn.net/feilong_csdn/article/details/88655927


三、glove中文词向量训练

glove可通过官方发布的模型来训练中文词向量,步骤如下

1、首先从官方下载glove并解压:

https://github.com/stanfordnlp/GloVe

2、将需要训练的预料处理好,做好分词去停用词处理,然后放到glove文件根目录下

3、修改demo.sh文件,共有两处修改,如下图所示:         

4、在glove主文件下即根目录下执行命令进行编译: make

5、在glove根目录下执行训练词向量命令: bash demo.sh  

如果训练数据大,训练时间长,使用如下命令训练词向量

nohupbash demo.sh > output.txt 2>&1 &

训练成功后,便会得到vectors.txt文件,可通过gensim的Word2Vec模块加载

glove训练得到的词向量效果如下:

gensim加载glove训练的词向量,glove和word2vec得到词向量文件区别在于word2vec包含向量的数量及其维度

可以使用gensim加载glove训练的词向量,因此先把glove格式词向量转化为word2vec的词向量,然后通过gensim.models.KeyedVectors.load_word2vec_format()加载glove训练的词向量模型


四、Elmo词向量训练

Elmo与word2vec\fasttext\glove最大的区别在于Elmo得到的是动态词向量,即ELMo得到的词向量不是固定的,是根据句子上下文语境有变化,Elmo训练词向量目前提供以下两种实现方式

1、训练英文词向量

结合tensorflow_hub库来实现,下面先给出一个简单的示例,从简单的示例中讲解如何利用tensorflow_hub库加载elmo模型进行词向量训练,再给出一个完整elmo示例代码,elmo预训练词向量用于下游任务

如上便是通过tensorflow_hub加载elmo模型对数据进行词向量预训练得到了output,我们先打印一下output看得到的是个什么东西

从上图可以看到elmo模型训练出来得到了一个字典,字典中key有elmo、default、lstm_output1、lstm_outtput2、word_emb、sequence_len,解释一个key的含义:

(1) sequence_len:输入中每个句子的长度

(2) word_emb:elmo的最开始一层的基于character的word embedding,shape为[batch_size, max_length, 512]

(3) lstm_outpus1/2:elmo中的第一层和第二层LSTM的隐状态输出,shape为[batch_size,max_length, 1024]

(4) default:前面得到的均为word级别的向量, default给出了使用mean-pooling求的句子级别的向量,即将上述elmo的所有词取平均

(5) elmo:每个词的输入层(word_emb),第一层LSTM输出,第二层LSTM输出的线性加权之后的最终的词向量,此外这个线性权重是可训练的,shape为[batch_size, max_length, 1024]

注意Attention,红色Attention:一般情况我们便是使用使用output[''elmo'']即可得到每个词的elmo词向量, 用于后续的任务

可以打印查看一下我们刚才训练得的可以用于下游任务的动态词向量

ELMO预训练接下游任务使用详细参见源代码

2、根据自己预料训练中文词向量模型

对官方发布的tensorflow的版本进行修改,训练自己的中文预料得到适用于中文词向量训练的elmo模型,大致步骤如下:

(1) 准备好中文预料分词后的数据

(2) 使用语料库生成词表数据

(3) 预训练word2vec词向量

(4) 下载github上bilm-tf代码https://github.com/allenai/bilm-tf

(5) 对bilm-tf代码进行修改训练中文词向量,下面将详细介绍如何操作

本次试验用的是头条新闻类分类数据

注意两点:

(1) word2vec预训练词向量只需要根据上面提到词向量训练方式对语料库进行预训练即可

(2) 词表数据vocab.data:使用语料库生成词表,但需要在词表开始额外添加三行<S>,</S>,<UNK>

这一点原因是因为bilm-tf源码中加载词表时首三行需要读入这个信息,如下图所示 

下载好bilm-tf源码后,下面我们着重介绍一下如何修改源码用于中文语料训练

(1) 修改bin/train_elmo.py文件

此文件为程序入口,修改部分如下

解释:

1、将load_vocab函数的第二个参数修改为None

2、设定运行elmo程序可见的GPU数

3、n_train_tokens:其大小间接影响程序迭代次数,可结合语料库大小进行设置

4、将此部分完全注释掉

(2) 修改bilm/train.py文件

如上图首先修改加载预训练词向量信息,初始化Word Embeddings,并同时将参数trainable设置为True,其次另一处修改如下图所示,将最终得到的model.embedding_weights保存到hdf5文件中

(3) 在bilm-tf目录下,启动训练程序,启动命令如下

nohuppython -u bin/train_elmo.py \

--train_prefix=''/nfs/project/wangyun/data/toutiao_word_corpus.txt''\

--vocab_file/nfs/project/wangyun/data/vocab.data \

--save_dir/nfs/project/wangyun/bilm-tf/model >output 2>&1 &

参数train_prefix是训练语料库路径

参数vocab_file是准备好的词表路径

参数save_dir是运行中模型保存路径

经过较长时间,运行结束后,产生模型文件如下

(4) 在bilm-tf目录下,运行bin/dump_weights.py,将checkpoint转换成hdf5文件

python-u  bin/dump_weights.py  \

--save_dir/nfs/project/wangyun/bilm-tf/model2 \

--outfile/nfs/project/wangyun/bilm-tf/model2/weights.hdf5

最终得到的模型文件如下:

至此elmo中文模型已经训练结束,已经得到了vocab.data对应的vocab_embedding.hdf5文件,以及elmo模型对应的weights.hdf5文件和options.json文件,可以使用usage_token.py文件训练得到词向量

(5)修改usage_token.py文件,运行usage_token.py文件得到词向量

python usage_token.py:便可得到词向量数据


五、Bert句向量和词向量训练

Bert训练句向量和词向量主要是利用了bert-as-service库进行训练,在服务器上安装bert-as-service环境,启动服务完成句向量和类似于elmo上下文相关的词向量训练,如下图所示:

注意由上述得到的是Word piece Embeddings而不是Word Embedding,因为使用Bert时,利用Bert模型Finetuning效果远比使用Bert Embedding效果好,因此这里不对Bert Embedding做详细介绍,如果想要使用可以参考以下两个网址,里面有详细介绍:

https://github.com/hanxiao/bert-as-service

https://bert-as-service./en/latest/tutorial/token-embed.html


六、Flair Embedding

FlairEmbedding来自Flair社区项目中的一个功能,Flair的功能包括

(1) flair是一个强大的NLP库,允许将最先进的模型应用在文本上,模型包括:NER命名实体识别,PoS词性标注,语义消歧和分类等

(2) flair支持多种语言,并且目前支持一个模型多个语言,即只用一个模型预测多种语言输入文本的NER任务和PoS任务

最后flair也是一个word embedding库,目前支持的有Flair Embedding、Bert Embedding、Elmo Embedding、Glove Embedding、Fasttext Embedding等,同时flair库还支持组合各种Word Embedding,通过加载Flair社区提供的预训练模型便可得到word embeddings,下面通过实例看如何使用,预训练模型到时候会提供给大家

首先我们看一下Flair Embedding的使用:

使用十分方便,Bert、Elmo、Glove、Fasttext Embedding使用方式也都大同小异,接下来我们在看一下如何组合各种Embedding模型

 

Flair除了提供Word Embeddings外,还提供了Character Embeddings(以char作为特征)和Byte Pair Embeddings(即将单词切分成子序列,粒度要大于char)

注意:对于Flair预训练模型下载需要能够翻墙,否则模型无法下载模型


    本站是提供个人知识管理的网络存储空间,所有内容均由用户发布,不代表本站观点。请注意甄别内容中的联系方式、诱导购买等信息,谨防诈骗。如发现有害或侵权内容,请点击一键举报。
    转藏 分享 献花(0

    0条评论

    发表

    请遵守用户 评论公约

    类似文章 更多