基于Doc2vec的段落向量训练及文本相似度计算

Doc2vec段落向量的训练方法,与训练词向量类似,段落向量的训练分为训练数据预处理和段落向量训练两个步骤。这里采用的是网上爬取的问答对中的query作为训练集,在段落向量训练之前必须进行训练数据预处理:中文分词,这里采用的是jieba分词。此外doc2vec在训练的时候能够采用tag信息来更好的辅助训练(表明是同一类doc),因此相对于word2vec模型,输入文档多了一个tag属性。

具体代码如下所示。这里解释一下doc2vec函数里各个参数的意思:

  1. docs:表示用于训练的语料文本
  2. size:代表段落向量的维度
  3. window:表示当前词和预测词可能的最大距离
  4. min_count:表示最小出现的次数
  5. workers:表示词向量训练时使用的线程数
  6. dm:表示训练时使用的模型种类,一般dm默认等于1,这是默认使用dm模型;当dm等于其他值时,使用DBOW模型训练词向量。

用到的Doc2vec的功能主要有三个:
    1.TaggedDocument语料预处理 
    2.train训练模型,save 和 load 加载训练好的模型 
    3.docvecs.most_similar 计算相似度

数据预处理,训练段落向量

import gensim
from gensim.models.doc2vec import Doc2Vec, LabeledSentence

TaggededDocument = gensim.models.doc2vec.TaggedDocument

def get_datasest():
    with open("train_after_process.txt", 'r', encoding='utf-8') as cf:
        docs = cf.readlines()
        print(len(docs))

    x_train = []
    # y = np.concatenate(np.ones(len(docs)))
    for i, text in enumerate(docs):
        word_list = text.split(' ')
        l = len(word_list)
        word_list[l - 1] = word_list[l - 1].strip()
        document = TaggededDocument(word_list, tags=[i])
        x_train.append(document)
    return x_train

# def getVecs(model, corpus, size):
#     vecs = [np.array(model.docvecs[z.tags[0]].reshape(1, size)) for z in corpus]
#     return np.concatenate(vecs)

def train(x_train, size=200, epoch_num=1):
    model_dm = Doc2Vec(x_train, min_count=1, window=3, size=size, sample=1e-3, negative=5, workers=4)
    model_dm.train(x_train, total_examples=model_dm.corpus_count, epochs=70)
    model_dm.save('model/model_dm_jiedai')

if __name__ == '__main__':
    x_train = get_datasest()
    model_dm = train(x_train)

加载训练好的模型并进行文本相似度计算:

和word2vec计算相似度类似,doc2vec计算文本相似度也主要包括如下三个步骤:数据预处理、文档向量化、计算文本相似。

详细代码如下所示,在doc2vec函数中,首先就是数据预处理操作,采用jieba分词对输入的句子进行分词(这里直接输入的文本格式是已经分好的,而且没有加入自定义词典);然后对句子向量化操作,通过加载训练好的模型,迭代找出合适的向量来代表文本。采用余弦相似度来进行向量相似度计算。最后经过相似度计算得到前10个最相似的句子。

import gensim
from gensim.models.doc2vec import Doc2Vec, LabeledSentence

TaggededDocument = gensim.models.doc2vec.TaggedDocument

def get_datasest():
    with open("train_after_process.txt", 'r',encoding='utf-8') as cf:
        docs = cf.readlines()
        print(len(docs))

    x_train = []
    # y = np.concatenate(np.ones(len(docs)))
    for i, text in enumerate(docs):
        word_list = text.split(' ')
        l = len(word_list)
        word_list[l - 1] = word_list[l - 1].strip()
        document = TaggededDocument(word_list, tags=[i])
        x_train.append(document)

    return x_train

def test():
    model_dm = Doc2Vec.load("model/model_dm_jiedai")
    test_text = ['朋友', '借', '了','钱', '不','还','怎么办']
    #句子向量化操作
    inferred_vector_dm = model_dm.infer_vector(test_text)
    print(inferred_vector_dm)
    sims = model_dm.docvecs.most_similar([inferred_vector_dm], topn=10)

    return sims

if __name__ == '__main__':
    x_train = get_datasest()
    sims = test()
    for count, sim in sims:
        sentence = x_train[count]
        words = ''
        for word in sentence[0]:
            words = words + word + ' '
        print(words, sim, len(sentence[0]))

测试结果:

        

小结:

通过实践,对于word2vec和doc2vec两种计算文本相似度的方法,一般对长文本语料进行训练时,采用doc2vec计算文本相似度的方法更胜一筹(由于语料限制,采用的是短文本语料训练的,结果不是很明显)。因为doc2vec不仅利用了词语的语义信息而且还综合了上下文语序的信息,而word2vec则通过向量相加求平均丢失了语序信息;word2vec计算长文本相似度时,关键词提取算法准确度不高,丢失了很多关键信息。

参考:http://linanqiu.github.io/2015/10/07/word2vec-sentiment/

上篇:向量化算法Doc2vec/str2vec/para2vec原理详解

 

评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Steven灬

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值