上一次提到了不错的学习聊天机器人的资源,不知道小伙伴们有没有去学习呢。
自己动手做聊天机器人教程
我最近每天都会学一点,拿出解读来和大家分享一下。

本文结构:

    1. 聊天机器人的架构简图
    1. 用 TensorFlow 实现 Chatbot 的模型
    1. 如何准备 chatbot 的训练数据
    1. Chatbot 源码解读

1. 聊天机器人的架构简图

学习资源:
[自己动手做聊天机器人 九-聊天机器人应该怎么做]
(http://www.shareditor.com/blogshow/?blogId=73)

聊天机器人的工作流程大体为:提问-检索-答案抽取。

提问:就是要分析主人的问句中关键词,提问类型,还有真正想知道的东西。

检索:根据前一步的分析,去找答案。

答案抽取:找到的答案,并不能直接应用,还要整理成真正有用的,可以作为答案的回答。

涉及到的关键技术如图中所示。

看不清图的话,就是酱紫:

问句解析:
中文分词、词性标注、实体标注、概念类别标注、句法分析、语义分析、逻辑结构标注、指代消解、关联关系标注、问句分类、答案类别确定;

海量文本知识表示:
网络文本资源获取、机器学习方法、大规模语义计算和推理、知识表示体系、知识库构建

答案生成与过滤:
候选答案抽取、关系推演、吻合程度判断、噪声过滤


2. 用 TensorFlow 实现 Chatbot 的模型

之前有根据 Siraj 的视频写过一篇《自己动手写个聊天机器人吧》,
文章里只写了主函数的简单过程:Data-Model-Training,是用 Lua 实现的,详细的代码可以去他的 github 上学习

下面这篇文章是用 TensorFlow + tflearn 库 实现,在 建模, 训练 和 预测 等环节可以学到更多细节:

学习资源:自己动手做聊天机器人 三十八-原来聊天机器人是这么做出来的

两篇的共同点是都用了 Seq2Seq 来实现。

LSTM的模型结构为:

细节的话可以直接去看上面那篇原文,这里 po 出建立模型阶段简要的流程图和过程描述:

  • 先将原始数据 300w chat 做一下预处理,即 切词,分为 问答对。

  • 然后用 word2vec 训练出词向量,生成二进制的词向量文件。

作为 Input data X 传入下面流程:

  • question 进入 LSTM 的 encoder 环节,answer 进入 decoder 环节,

  • 分别生成 output tensor。

  • 其中 decoder 是一个词一个词的生成结果,将所有结果加入到一个 list 中。

  • 最后和 encoder 的输出,一起做为下一环节 Regression 的输入,并传入 DNN 网络。


3. 如何准备 chatbot 的训练数据

学习资源:
自己动手做聊天机器人 三十八-原来聊天机器人是这么做出来的

训练数据的生成过程如下:

  • 首先在 input file 里读取每一行,并根据 ‘|’ 拆分成 question 和 answer 句子。
  • 每个句子,都将 word 通过 word2vec 转化成词向量。
  • 每一句的向量序列都转化成相同维度的形式:self.word_vec_dim * self.max_seq_len
  • 最后 answer 构成了 y 数据,question+answer 构成了 xy 数据,再被投入到 model 中去训练:
model.fit(trainXY, trainY, n_epoch=1000, snapshot_epoch=False, batch_size=1)

代码如下:

def init_seq(input_file):"""读取切好词的文本文件,加载全部词序列"""file_object = open(input_file, 'r')vocab_dict = {}while True:question_seq = []answer_seq = []line = file_object.readline()if line:line_pair = line.split('|')line_question = line_pair[0]line_answer = line_pair[1]for word in line_question.decode('utf-8').split(' '):if word_vector_dict.has_key(word):question_seq.append(word_vector_dict[word])for word in line_answer.decode('utf-8').split(' '):if word_vector_dict.has_key(word):answer_seq.append(word_vector_dict[word])else:breakquestion_seqs.append(question_seq)answer_seqs.append(answer_seq)file_object.close()
def generate_trainig_data(self):xy_data = []y_data = []for i in range(len(question_seqs)):question_seq = question_seqs[i]answer_seq = answer_seqs[i]if len(question_seq) < self.max_seq_len and len(answer_seq) < self.max_seq_len:sequence_xy = [np.zeros(self.word_vec_dim)] * (self.max_seq_len-len(question_seq)) + list(reversed(question_seq))sequence_y = answer_seq + [np.zeros(self.word_vec_dim)] * (self.max_seq_len-len(answer_seq))sequence_xy = sequence_xy + sequence_ysequence_y = [np.ones(self.word_vec_dim)] + sequence_yxy_data.append(sequence_xy)y_data.append(sequence_y)return np.array(xy_data), np.array(y_data)

4. Chatbot 源码解读

学习资源:
自己动手做聊天机器人 三十八-原来聊天机器人是这么做出来的

这篇文章在 github 上的源码:

提炼出步骤如下:

其中 2. 准备数据, 3. 建立模型 就是上文着重说的部分。

    1. 引入包
    1. 准备数据
    1. 建立模型
    1. 训练
    1. 预测

1. 引入包

import sys
import math
import tflearn
import tensorflow as tf
from tensorflow.python.ops import rnn_cell
from tensorflow.python.ops import rnn
import chardet
import numpy as np
import struct

2. 准备数据

def load_word_set()
将 3000 万语料,分成 Question 和 Answer 部分,提取出 word。

def load_word_set():file_object = open('./segment_result_lined.3000000.pair.less', 'r')while True:line = file_object.readline()if line:line_pair = line.split('|')line_question = line_pair[0]line_answer = line_pair[1]for word in line_question.decode('utf-8').split(' '):word_set[word] = 1for word in line_answer.decode('utf-8').split(' '):word_set[word] = 1else:breakfile_object.close()

def load_vectors(input)
从 vectors.bin 加载词向量,返回一个 word_vector_dict 的词典,key 是词,value 是200维的向量。

def init_seq(input_file)
将 Question 和 Answer 中单词对应的词向量放在词向量序列中 question_seqs, answer_seqs

def init_seq(input_file):"""读取切好词的文本文件,加载全部词序列"""file_object = open(input_file, 'r')vocab_dict = {}while True:question_seq = []answer_seq = []line = file_object.readline()if line:line_pair = line.split('|')line_question = line_pair[0]line_answer = line_pair[1]for word in line_question.decode('utf-8').split(' '):if word_vector_dict.has_key(word):question_seq.append(word_vector_dict[word])for word in line_answer.decode('utf-8').split(' '):if word_vector_dict.has_key(word):answer_seq.append(word_vector_dict[word])else:breakquestion_seqs.append(question_seq)answer_seqs.append(answer_seq)file_object.close()

def vector_sqrtlen(vector)
用来求向量的长度。

def vector_sqrtlen(vector):len = 0for item in vector:len += item * itemlen = math.sqrt(len)return len

def vector_cosine(v1, v2)
用来求两个向量间的距离。

def vector_cosine(v1, v2):if len(v1) != len(v2):sys.exit(1)sqrtlen1 = vector_sqrtlen(v1)sqrtlen2 = vector_sqrtlen(v2)value = 0for item1, item2 in zip(v1, v2):value += item1 * item2return value / (sqrtlen1*sqrtlen2)

def vector2word(vector)
给定一个词向量,去 word-vector 字典中查找与此向量距离最近的向量,并记忆相应的单词,返回单词和 cosine 值。

def vector2word(vector):max_cos = -10000match_word = ''for word in word_vector_dict:v = word_vector_dict[word]cosine = vector_cosine(vector, v)if cosine > max_cos:max_cos = cosinematch_word = wordreturn (match_word, max_cos)

3. 建立模型

class MySeq2Seq(object)
在前两篇笔记中单独写了这两块。

def generate_trainig_data(self)
question_seqs, answer_seqs 得到 xy_data 和 y_data 的形式。

def model(self, feed_previous=False)
用 input data 生成 encoder_inputs 和带GO头的 decoder_inputs
将 encoder_inputs 传递给编码器,返回一个输出(预测序列的第一个值)和一个状态(传给解码器)。
在解码器中,用编码器的最后一个输出作为第一个输入,预测过程用前一个时间序的输出作为下一个时间序的输入。

4. 训练

def train(self)
generate_trainig_data() 生成 X y 数据,传递给 上面定义的 model,并训练 model.fit,再保存。

    def train(self):trainXY, trainY = self.generate_trainig_data()model = self.model(feed_previous=False)model.fit(trainXY, trainY, n_epoch=1000, snapshot_epoch=False, batch_size=1)model.save('./model/model')return model

5. 预测

generate_trainig_data() 生成数据,用 model.predict 进行预测,predict 结果的每一个 sample 相当于一句话的词向量序列,每个 sample 中的每个 vector 在 word-vector 字典中找到与其最近的向量,并返回对应的 word,及二者间的 cosine。

if __name__ == '__main__':phrase = sys.argv[1]if 3 == len(sys.argv):my_seq2seq = MySeq2Seq(word_vec_dim=word_vec_dim, max_seq_len=max_seq_len, input_file=sys.argv[2])else:my_seq2seq = MySeq2Seq(word_vec_dim=word_vec_dim, max_seq_len=max_seq_len)if phrase == 'train':my_seq2seq.train()else:model = my_seq2seq.load()trainXY, trainY = my_seq2seq.generate_trainig_data()predict = model.predict(trainXY)for sample in predict:print "predict answer"for w in sample[1:]:(match_word, max_cos) = vector2word(w)#if vector_sqrtlen(w) < 1:#    breakprint match_word, max_cos, vector_sqrtlen(w)

推荐阅读
历史技术博文链接汇总
也许可以找到你想要的

用 TensorFlow 做个聊天机器人相关推荐

  1. Tensorflow搞一个聊天机器人

     Tensorflow搞一个聊天机器人 catalogue 0. 前言 1. 训练语料库 2. 数据预处理 3. 词汇转向量 4. 训练 5. 聊天机器人 - 验证效果 0. 前言 不是搞机器学习 ...

  2. python制作聊天机器人原理_用 Python 来做一个聊天机器人吧!(一)

    在我的一个回答里,我提到了用 Python 搭建聊天机器人.从今天开始,我就带着大家从0开始搭建一个聊天机器人. (顺便说一句,我喜欢把链接像上面这样加在文字里,如果找不到文中所说的资源,可以看看周围 ...

  3. 机器学习做自动聊天机器人_我和一个治疗机器人聊天,缓解了我对Covid的恐惧。 这很奇怪。

    机器学习做自动聊天机器人 重点 (Top highlight) On a hot afternoon in June, I downloaded a free mental health app ca ...

  4. 机器学习做自动聊天机器人_您不应该使用聊天机器人的3个原因

    机器学习做自动聊天机器人 现在,基于云的聊天机器人几乎是旧技术. 他们已经有四年了. 和接待肯定是混合的 . 上周,几家合作机构的研究人员公布了正式的书面内容,称为``第二次对话智能挑战赛'',这是聊 ...

  5. 来做一个聊天机器人吧[1]

    来做一个聊天机器人吧[1] 前言 准备 GUI开发 聊天模块1.0版本 语音合成1.0版本 版本1.0 前言 课程设计自己选了这个课题,因为之前就对NLP(Natural Language Proce ...

  6. 机器学习做自动聊天机器人_当您14岁时建立和销售聊天机器人会是什么样的感觉...

    机器学习做自动聊天机器人 by Alec Jones 通过亚历克琼斯 当您14岁时建立和销售聊天机器人会是什么样的感觉 (What it's like to build and market a ch ...

  7. 【NLP实战】如何基于Tensorflow搭建一个聊天机器人

    实战是学习一门技术最好的方式,也是深入了解一门技术唯一的方式.因此,NLP专栏计划推出一个实战专栏,让有兴趣的同学在看文章之余也可以自动动手试一试. 本篇介绍如何基于tensorflow快速搭建一个基 ...

  8. Python做个聊天机器人(单身狗治愈神器)

    受到疫情的影响,今年的这个假期显得格外的长,可能是我国建国以来最长的一次的吧.很多同学们大呼"我第一次这么想去上学","去年在家捡蘑菇,今年在家长蘑菇",&qu ...

  9. 巧用提示语,说说话就能做个聊天机器人

    你好,我是徐文浩. 这一讲,我们来看看Open AI提供的Completion这个API接口.相信已经有不少人试过和ChatGPT聊天了,也有过非常惊艳的体验,特别是让ChatGPT帮我们写各种材料. ...

最新文章

  1. asp.net弹出div层,并把弹出层上的值赋值给界面
  2. 常用单词缩写(不断更新)
  3. 熟悉的亲切-老外婆教做的豌豆蔬菜汤
  4. python爬虫应用实战-如何爬取好看的小姐姐照片?
  5. ajax burp 乱码,burp suite中国乱码的解决方案
  6. Photo.scr病毒
  7. wcf wpf mfc 区别
  8. 科目三路考需准备事项
  9. python 持续集成部署_Jenkins部署git+python项目实现持续集成
  10. system函数阻塞_简单的Java阻塞队列
  11. pythonyaml参数_使用python检查yaml配置文件是否符合要求
  12. delphi 选择文件夹目录_系统小技巧:不装软件 批处理为文件夹加锁
  13. asp.net中异步调用WebService(异步页)[转]
  14. HBuilder开发app,扫描枪中,使用input输入框,然后点击扫描,获取不到条码!
  15. .ps格式的文件怎么打开?
  16. 《如何阅读一本书》——读书方法的整理
  17. 技术干货 | 实现模型透明化的有效技术:MindSpore可解释AI能力
  18. [20191206]隐含参数_db_always_check_system_ts.txt
  19. 用Nextcloud搭建个人网盘
  20. 考研高数常用公式汇总(上)

热门文章

  1. 小白学 Python(1):开篇
  2. 好全的前端只是体系(前端架构师来找找有木有你想要的) 五
  3. 修改我的世界服务器怪物爆率,精英生成概率以及部分能力参数设置_我的世界精英怪mod教程如何调控怪物属性和掉落物__单机攻略_跑跑车单机游戏网...
  4. AWS 中文入门开发教学 21- 通过 Web 应用连接到 MySQL 数据库服务器
  5. 木板切割问题——贪心
  6. QPushButton 实现保持按下效果(转载​​)
  7. 计算机网络 之 DNS (Domain Name System)域名服务器
  8. Android设备root及xposedPrivacy的安装
  9. 《两化融合 数字化转型 价值效益参考模型》国家标准全文
  10. 软件开发随笔系列一——分布式架构实现