QA: Dynamic Memory Networks for Natural Language Processing

来源:互联网 发布:柠檬网络电视 | 柠檬tv 编辑:程序博客网 时间:2024/05/18 02:36

摘要

我们提出一种动态内存网络(DMN)的方式,来解决,输入多个描述句子和问题来生成答案的这种场景。

简介

Question answering (QA):根据上下文(文本,图片等),结合问题(question), 来生成答案
dynamic memory network (DMN):它是一种网络结构,处理的是(context_input-querstion-answer)这样的三元组。
inputs: 提前需要记住的上下文输入
querstion: 问题
answer: 输出

这里写图片描述

网络框架

DMN的目标是: 先将输入的inputs encoding 成一个向量,然后这个向量结合question 来生成answer

各个模块的介绍:
Input Module

处理的是这个问题的上下文输入,比如一段话,一个图片,视频等。然后将这个原始信息encoding 成一个向量。

Semantic Memory Module

这个模块存储的是通用的语义内容,比如知识图谱,词向量等

Question Module:

这个模块将原始的文本问题通过计算后生成向量,然后这些向量触发episodic memory module开始迭代计算

episodic memory module

DMN的核心,这个模块根据问题,从输入模块中选取相关的信息,然后开始迭代,生成一个表示

Answer Module
将episodic memory module输出的表示生成答案


这里写图片描述

详细介绍:

Input Module

后续我们称每一个输入的上下文是一个fact,我们的目标是对facts进行encodding 生成一个向量。
我们先不考虑图片的问题

  • 输入是一段话:

    TI=(wI1,wI2,,...,wITI) 
    TI是对fact的词个数,那我们直接将这个序列输入一个序列模型,
    比如(LSTM,GRU)等,会得到一个状态向量ct
    它的shape是:
    [batch_size, sentence_count, word_dim] = [batch大小,词的个数,词向量的长度]

    c_t, _ = tf.nn.dynamic_rnn(gru_cell, input, T_I, dtype=tf.float32)
  • 输入的是n句话:

    facts=(fact1,fact2,...,factF)
    facti=(wi1,wi2,...,wiL)

    其中F是input的输入句子数量,L是每个句子最长的值,我们将facts写成矩阵的形式
    他的shape是:
    [batch_size, fact_count, sentence_count, word_dim] = [batch大小,fact个数,词的个数,词向量的长度]

    这里有两种处理方式:

    • 直接将facts 变成一段话,得到 F*L 个序列 将这L个序列进入序列模型

      facts = tf.reshape(facts, [batch_size, F * L, word_dim])c_t, _ = tf.nn.dynamic_rnn(gru_cell, facts, F * L, dtype=tf.float32)
    • 将每个fact的向量直接相加,然后得到L个序列

      facts = tf.reduce_sum(facts, 2)c_t, _ = tf.nn.dynamic_rnn(gru_cell, facts, L, dtype=tf.float32)

    ct这个向量就是我们需要输入内存的向量

Semantic Memory Module

  1. 保存基本概念,比如知识图谱
  2. 基础的词向量等

Question Module

question mudule很简单,question的输入是一个问题TQ=(wQ1,wQ2,...,wQt)
将这个序列通过seq model后得到的state即可:

ques_embed = tf.nn.embedding_lookup(embedding, question)  # [N, Q, V]ques_embed = tf.unstack(ques_embed, axis=1)  # Q X [N, V]_, question_vec = tf.nn.static_rnn(gru, ques_embed, dtype=tf.float32)  # [N, d]

Episodic Memory Module

它的作用是根据问题从输入的上下文中选出相关的facts,然后根据这些facts生成一个合理的表示memory,这个表示输出到answer module。

然后这个模块可以多次处理这些facts,每次处理这些facts可以聚焦不同的点。每次通过后就生成一个 episodic, 然后所有的episodic都被归结成一个memory。

所以episodic memory module 是一种attention 机制,这个机制简单描述是:

  1. 将所有的facts通过attention机制聚焦,生成episodic
  2. 将所有的episodic归纳成memory

我们从后开始介绍:
memory是经过多次迭代得到的,
我们令这个内存memory序列为:m1,m2,...,mTp
episodic序列为:e1,e2,...,et
那么meory的迭代如下:
mi=GRU(ei,mi1) m0=q

memory = question_vecmemory, _ = gru(e_i, memory)

最终输出的memory m=mTp

下面我们给出ei的计算逻辑,上面介绍了,ei就是第i次通过迭代facts时得到的episodic,
那它的计算和facts有关,上面在Input module我们介绍过,facts encoding出来的结果是ct
我们令 t 的最大长度为 TC
所以 episodic 是ct经过TC长度的seq model的结果,但是简单的GRU,还加了gate权重

hit=EP(ct,hit1)
ei=hiTC

这里 EP 是呆权重因子的序列模型,我们令第i次迭代的attention机制通过gate weight 方式实现

EP(ct,hit1)=gitGRU(ct,hit1)+(1git)hit1

现在我们开始计算gate 权重,它是一个sigmoid函数:
git=G(ct,mi1,q)
G(c,m,q)=σ(W2tanh(W1z(c,m,q)+b1)+b2)
z(c,m,q)=[c,m,q,cq,cm,|cq|,|cm|,cTWbq,cTWbm]

到此我们就完成了
input facts => episodic => memory 的计算

Answer Sequence

上面的模块最终生成了memory m,这个模块就是根据m生成答案

这里还是一个序列模型,比如GRU,它的初始状态 a0=m
然后生成答案(seq2seq里面的decode步骤)
at=GRU([yt1,q],at1)
yt=softmax(Waat)

训练数据

face book 发布的 bAbI

原创粉丝点击