精华内容
下载资源
问答
  • tensorflow 双向RNN

    2018-07-10 15:47:15
    基于tensorflow1.8实现的单层静态双向RNN网络,以mnist手写体为测试用例
  • 双向RNN原始论文

    2017-08-07 16:05:36
    双向RNN原始论文
  • 在复杂的城市环境中,由于存在难以避免的GNSS定位信号中断现象以及车辆行驶过程中的误差累积,易造成所收集的车辆轨迹数据不准确和不完备,因此提出一种基于双向 RNN 的私家车轨迹重构算法,使用了GNSS-OBD轨迹采集...
  • 今天小编就为大家分享一篇浅谈Tensorflow 动态双向RNN的输出问题,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
  •  因为时刻t的输出不仅取决于之前时刻的信息,还取决于未来的时刻,所以有了双向RNN。比如要预测一句话中间丢失的一个单词,有时只看上文是不行的,需要查看上下文。原理也和RNN差不多,只不过将是将句子中的每个...

    RNN:

    在这里插入图片描述

    在这里插入图片描述

    公式:

    在这里插入图片描述

    多层RNN,前层的输出ht作为后层的输入xt:

    在这里插入图片描述

    双向RNN:

    因为时刻t的输出不仅取决于之前时刻的信息,还取决于未来的时刻,所以有了双向RNN。比如要预测一句话中间丢失的一个单词,有时只看上文是不行的,需要查看上下文。原理也和RNN差不多,只不过将是将句子中的每个token的向量按句子倒序一个个传入RNN。正向时用正向权重计算,反向时用反向权重计算。
    正向计算和反向计算的权重不共享。

    nn.RNN(input_size, 
    		hidden_size, 
    		num_layers=1, 
    		nonlinearity=tanh, 
    		bias=True, 
    		batch_first=False, 
    		dropout=0, 
    		bidirectional=False)
    


    input_size:表示输入 xt 的特征维度
    hidden_size:表示输出的特征维度
    num_layers:表示网络的层数
    nonlinearity:表示选用的非线性激活函数,默认是 ‘tanh’
    bias:表示是否使用偏置,默认使用
    batch_first:表示输入数据的形式,默认是 False,就是这样形式,(seq, batch, feature),也就是将序列长度放在第一位,batch 放在第二位
    dropout:表示是否在输出层应用 dropout
    bidirectional:表示是否使用双向的 rnn,默认是 False。

    import  torch
    from    torch import nn
    from    torch.nn import functional as F
    rnn = nn.RNN(input_size=10, hidden_size=20, num_layers=2)
    # 可理解为一个字串长度为5(RNN训练时每个字符一个个传进去,一个字符代表一个时刻t), batch size为3, 字符维度为10的输入
    input_tensor  = torch.randn(5, 3, 10)
    # 两层RNN的初始H参数,维度[layers, batch, hidden_len]
    h0 = torch.randn(2, 3, 20)
    # output_tensor最后一层所有状态!!!!!的输出(看上面那个多层的RNN图最后一层会输出h1,h2....hn)
    #hn(也即Cn)表示两层最后一个时序的状态输出
    output_tensor, hn =rnn(input_tensor, h0)
    print(output_tensor.shape, hn.shape)
    

    torch.Size([5, 3, 20]) torch.Size([2, 3, 20])

    从上面可以看到输出的h,x,和输入的h,x维度一致。
    上面的参数中,num_layers=2相当于有两个rnn cell串联,即一个的输出h作为下一个的输入x。也可单独使用两个nn.RNNCell实现

    而当我们设置成双向RNN时,即bidirectional=True

    rnn = nn.RNN(input_size=10, hidden_size=20, num_layers=2,bidirectional=True) 
    h0 = torch.randn(4,3, 20)
    

    torch.Size([5, 3, 40]) torch.Size([4, 3, 20])

    一共5个时刻,可以看到最后一时刻的output维度是[3, 40],因为nn.rnn模块他在最后会将正向和反向的结果进行拼接concat。而hn中的4是指正反向,还有因为num_layers是两层所以为4。

    基于RNN(多层RNN、双向RNN只需修改两个参数即可实现)的英文文本分类:

    数据集:英文电影评论(积极、消极)二分类

    分词表是我自己修改了nltk路径:
    C:\用户\AppData\Roaming\nltk_data\corpora\stopwords里的english文件。
      然后你把我的my_english文件放进里面就可以,或者你直接用它的english
      数据集链接和my_english分词表都在以下网盘链接:
    链接:https://pan.baidu.com/s/1vhh5FmU01KqyjRtxByyxcQ
    提取码:bx4k

    关于词嵌入是用了nn.embedding(),它的用法请看这:点击进入

    import torch
    import numpy as np
    import pandas as pd
    import torch.nn as nn
    import torch.optim as optim
    import torch.utils.data as Data
    import torch.nn.functional as F
    

    读入数据集,数据集为电影评论数据(英文,一个24500条数据),分为积极和消极两类:

    df = pd.read_csv('Dataset.csv')
    print('一共有{}条数据'.format(len(df)))
    df.info()
    

    分词去停用词,我的csv文件里已经处理完保存好了分词结果,可以不运行这一部分:

    from nltk.corpus import stopwords
    import nltk
    def separate_sentence(text):
        disease_List = nltk.word_tokenize(text)
        #去除停用词
        filtered = [w for w in disease_List if(w not in stopwords.words('my_english'))]
        #进行词性分析,去掉动词、助词等
        Rfiltered =nltk.pos_tag(filtered)
        #以列表的形式进行返回,列表元素以(词,词性)元组的形式存在
        filter_word = [i[0] for i in Rfiltered]
        return " ".join(filter_word)
    df['sep_review'] = df['review'].apply(lambda x:separate_sentence(x))
    

    根据需要筛选数据(这里我使用了1000条):

    #用xxx条玩玩
    use_df = df[:1000]
    use_df.head(10)
    sentences = list(use_df['sep_review'])
    labels = list(use_df['sentiment'])
    

    小于最大长度的补齐:

    max_seq_len = max(use_df['sep_review'].apply(lambda x: len(x.split())))
    PAD = ' <PAD>'  # 未知字,padding符号用来填充长短不一的句子(用啥符号都行,到时在nn.embedding的参数设为padding_idx=word_to_id['<PAD>'])即可
    
    #小于最大长度的补齐
    for i in range(len(sentences)):
        sen2list = sentences[i].split()
        sentence_len = len(sen2list)
        if sentence_len<max_seq_len:
            sentences[i] += PAD*(max_seq_len-sentence_len)  
    

    制作词表(后面用来给单词编号):

    num_classes = len(set(labels))  # num_classes=2
    word_list = " ".join(sentences).split()
    vocab = list(set(word_list))
    word2idx = {w: i for i, w in enumerate(vocab)}
    vocab_size = len(vocab)
    

    给单词编号(编完号后续还要在embeding层将其转成词向量):

    def make_data(sentences, labels):
        inputs = []
        for sen in sentences:
            inputs.append([word2idx[n] for n in sen.split()])
    
        targets = []
        for out in labels:
            targets.append(out) # To using Torch Softmax Loss function
        return inputs, targets
    
    input_batch, target_batch = make_data(sentences, labels)
    input_batch, target_batch = torch.LongTensor(input_batch), torch.LongTensor(target_batch)
    

    用Data.TensorDataset(torch.utils.data)对给定的tensor数据(样本和标签),将它们包装成dataset,
    然后用Data.DataLoader(torch.utils.data)数据加载器,组合数据集和采样器,并在数据集上提供单进程或多进程迭代器。它可以对我们上面所说的数据集dataset作进一步的设置(比如可以设置打乱,对数据裁剪,设置batch_size等操作,很方便):

    from sklearn.model_selection import train_test_split
    # 划分训练集,测试集
    x_train,x_test,y_train,y_test = train_test_split(input_batch,target_batch,test_size=0.2,random_state = 0)
    
    train_dataset = Data.TensorDataset(torch.tensor(x_train), torch.tensor(y_train))
    test_dataset = Data.TensorDataset(torch.tensor(x_test), torch.tensor(y_test))
    dataset = Data.TensorDataset(input_batch, target_batch)
    
    batch_size = 16
    train_loader = Data.DataLoader(
        dataset=train_dataset,      # 数据,封装进Data.TensorDataset()类的数据
        batch_size=batch_size,      # 每块的大小
        shuffle=True,               # 要不要打乱数据 (打乱比较好)
        num_workers=2,              # 多进程(multiprocess)来读数据
    )
    test_loader = Data.DataLoader(
        dataset=test_dataset,      # 数据,封装进Data.TensorDataset()类的数据
        batch_size=batch_size,      # 每块的大小
        shuffle=True,               # 要不要打乱数据 (打乱比较好)
        num_workers=2,              # 多进程(multiprocess)来读数据
    )
    

    搭建网络:

    device = torch.device("cuda" if torch.cuda.is_available() else "cpu")
    print(device,'能用')
    class RNN(nn.Module):
        def __init__(self,vocab_size, embedding_dim, hidden_size, num_classes, num_layers,bidirectional):
            super(RNN, self).__init__()
            self.vocab_size = vocab_size
            self.embedding_dim = embedding_dim
            self.hidden_size = hidden_size
            self.num_classes = num_classes
            self.num_layers = num_layers
            self.bidirectional = bidirectional
            
            self.embedding = nn.Embedding(self.vocab_size, embedding_dim, padding_idx=word2idx['<PAD>'])
            self.rnn = nn.RNN(input_size=self.embedding_dim, hidden_size=self.hidden_size,batch_first=True,num_layers=self.num_layers,bidirectional=self.bidirectional)
            if self.bidirectional:
                self.fc = nn.Linear(hidden_size*2, num_classes)
            else:
                self.fc = nn.Linear(hidden_size, num_classes)
            
        def forward(self, x):
            batch_size, seq_len = x.shape
            #初始化一个h0,也即c0,在RNN中一个Cell输出的ht和Ct是相同的,而LSTM的一个cell输出的ht和Ct是不同的
            #维度[layers, batch, hidden_len]
            if self.bidirectional:
                h0 = torch.randn(self.num_layers*2, batch_size, self.hidden_size).to(device)
            else:
                h0 = torch.randn(self.num_layers, batch_size, self.hidden_size).to(device)
            x = self.embedding(x)
            out,_ = self.rnn(x, h0)
            output = self.fc(out[:,-1,:]).squeeze(0) #因为有max_seq_len个时态,所以取最后一个时态即-1层
            return output   
    

    实例化网络:
    要实现多层RNN只需修改参数:num_layers。要实现双向RNN只需修改参数:bidirectional=True。

    model = RNN(vocab_size=vocab_size,embedding_dim=300,hidden_size=20,num_classes=2,num_layers=2,bidirectional=True).to(device)
    criterion = nn.CrossEntropyLoss().to(device)
    optimizer = optim.Adam(model.parameters(), lr=1e-3)
    

    模型训练过程:

    model.train()
    for epoch in range(1):
        for batch_x, batch_y in train_loader:
            batch_x, batch_y = batch_x.to(device), batch_y.to(device)
            pred = model(batch_x)
            loss = criterion(pred, batch_y)  #batch_y类标签就好,不用one-hot形式   
            
            if (epoch + 1) % 10 == 0:
                print('Epoch:', '%04d' % (epoch + 1), 'loss =', '{:.6f}'.format(loss))
            optimizer.zero_grad()
            loss.backward()
            optimizer.step()
    
    

    模型测试过程:这里只测试准确率

    test_acc_list = []
    model.eval()
    test_loss = 0
    correct = 0
    with torch.no_grad():
        for data, target in test_loader:
            data, target = data.to(device), target.to(device)
            output = model(data)
            pred = output.max(1, keepdim=True)[1]                           # 找到概率最大的下标
            correct += pred.eq(target.view_as(pred)).sum().item()
    
    # test_loss /= len(test_loader.dataset)
    # test_loss_list.append(test_loss)
    test_acc_list.append(100. * correct / len(test_loader.dataset))
    print('Accuracy: {}/{} ({:.0f}%)\n'.format(correct, len(test_loader.dataset),100. * correct / len(test_loader.dataset)))
    
    展开全文
  • 双向 RNN

    2018-12-04 17:05:00
     双向 RNN 结合时间上从序列起点开始移动的 RNN 和另一个时间上从序列末尾开始移动的 RNN 2.逻辑图    其中 h (t) 代表通过时间向前移动的子 RNN 的状态,g (t) 代表通过时间向后移动的子 RNN 的状态  允许...

    1.基本理论

      双向 RNN 结合时间上从序列起点开始移动的 RNN 和另一个时间上从序列末尾开始移动的 RNN

    2.逻辑图

      

        其中 h (t) 代表通过时间向前移动的子 RNN 的状态,g (t) 代表通过时间向后移动的子 RNN 的状态

        允许输出单元 o (t) 能够计算同时依赖于过去和未来且对时刻 t 的输入值最敏感的表示,而不必指定 t 周围固定大小的窗口

    转载于:https://www.cnblogs.com/bigcome/p/10065236.html

    展开全文
  • 双向RNN:bidirectional_dynamic_rnn()函数的使用详解 先说下为什么要使用到双向RNN,在读一篇文章的时候,上文提到的信息十分的重要,但这些信息是不足以捕捉文章信息的,下文隐含的信息同样会对该时刻的语义产生...
  • 双向RNN原理

    千次阅读 2020-05-05 22:44:01
    就是使用双向RNN,它能使得我们在序列的某点处,不仅获取之前的信息,还能获取将来的信息。 将来的信息是什么意思呢?为什么根据之前的信息还不足够网络做决策? 我们看下面的一个例子:用传统RNN做NER,判定某个...

    1. 引入

    我们之前已经了解了RNN中的GRU[2]和LSTM[3]。

    怎么样才能进一步优化RNN这样的模型呢?就是使用双向RNN,它能使得我们在序列的某点处,不仅获取之前的信息,还能获取将来的信息。

    将来的信息是什么意思呢?为什么根据之前的信息还不足够网络做决策?

    我们看下面的一个例子:用传统RNN做NER,判定某个单词是否为人名。

    在这里插入图片描述

    例子中给出的两句话,第一句话中的Teddy不是人名(是泰迪熊玩具),第二句话中的才是人名。

    我们可以看到,要判断Teddy是否为人名,如果仅仅根据它之前的信息(“He said”),是难以进行判断的。

    这就是单向RNN的困境。不仅仅是RNN,单向的GRU/LSTM都存在这样的问题。

    2. 双向RNN的原理

    那双向RNN是如何解决这个问题的呢?

    例如,输入一个句子,有四个单词,每个单词用x表示,双向RNN如下图所示。

    在这里插入图片描述

    其中紫色部分的框图和连接线表示原始的单向RNN,他们依次从左向右连接。

    绿色的部分,表示反向连接,他们依次反向向前连接。

    这个网络构成了一个无环图。给定一个输入序列(x<1>,…,x<4>),这个网络首先进行前向计算(正向),依次得到正向a<1>, a<2>, a<3>, a<4>的值;然后进行反向计算,依次得到反向a<4>, a<3>, a<2>, a<1>的值。

    这样,给定一个句子:“He said,Teddy Roosevelt”,要判断Teddy是否为人名,这个双向网络就会考虑之前的信息“He said”,也会考虑之后的信息“Roosevelt”,来综合做判断。

    这就是双向RNN。上图中的基本单元,可以为RNN单元,也可以是GRU单元,或者是LSTM单元。

    3. 双向网络

    根据上面的原理,我们可以有很多种双向序列模型:

    • 双向RNN
    • 双向GRU
    • 双向LSTM

    双向序列模型的优点,是可以考虑整个句子的信息,即使在句子中间,也可以综合考虑过去的信息和将来的信息。

    当然,它也有缺点:

    • 需要完整数据的序列,你才能预测任意位置。

    举个例子,比如语音识别系统中,这就要求你必须等待一个人说完整句话,才能做出识别,这样就有一个比较长的等待时间。

    但是对于很多NLP的应用,你可以获取完整的整个句子,那这个标准的双向RNN算法就很高效。

    4. 参考

    • [1]. Andrew Ng Sequence Models video
    • [2]. https://blog.csdn.net/ybdesire/article/details/105374720
    • [3]. https://blog.csdn.net/ybdesire/article/details/105621683
    展开全文
  • 本文讲解循环神经网络(RNN)的改进方法,并使用改进的RNN实现电影评论情感分析。 本人全部文章请参见:博客文章导航目录 本文归属于:NLP模型原理与应用系列 前文:长短期记忆网络(LSTM)原理与实战 2. 多层RNN...

    1. 前言

    本文讲解循环神经网络(RNN)的改进方法,并使用改进的RNN实现电影评论情感分析。
    本人全部文章请参见:博客文章导航目录
    本文归属于:自然语言处理系列
    本系列实践代码请参见:我的GitHub
    前文:长短期记忆网络(LSTM)原理与实战
    后文:Sequence-to-Sequence模型原理

    2. 多层RNN(Stacked RNN)

    在深度学习领域,可以将许多全连接层堆叠,构成一个多层感知机(Multi-Layer Perception),可以将许多卷积层堆叠,构成一个深度卷积网络。同样的,可以将许多RNN层堆叠,构成一个多层RNN网络。
    RNN每读取一个新的输入 x t x_t xt,就会生成状态向量 h t h_t ht作为当前时刻的输出和下一时刻的输入状态。 将 T T T个输入 x 0 ∼ x T x_0\sim x_T x0xT依次输入RNN,相应地会产生 T T T个输出。第一层RNN输出的 T T T个状态向量可以作为第二层RNN的输入,第二层RNN拥有独立的参数,依次读取 T T T个来自第一层RNN的状态向量,产生 T T T个新的输出。第二层RNN输出的 T T T个状态向量可以作为第三层RNN的输入,依此类推,构成一个多层RNN网络。
    图一
    在图一所示3层RNN网络中,输入为词嵌入 x 0 ∼ x t x_0\sim x_t x0xt,状态向量 h 1 ∼ h t h_1\sim h_t h1ht是最终的输出。可以将最后一个状态向量 h t h_t ht看做是从最底层输入的文本中提取的特征向量。
    当训练数据足够多时,多层RNN效果可能会比单层RNN效果好,可以尝试使用多层RNN。

    3. 双向RNN(Bidirectional RNN)

    RNN对时序数据的处理与人脑一致,人类从左往右依次阅读文本中的每个单词,在大脑里积累信息,RNN从左往右依次读取输入 x t , ( t = 0 ∼ T ) x_t, (t=0\sim T) xt,(t=0T),在状态向量 h t , ( t = 0 ∼ T ) h_t, (t=0\sim T) ht,(t=0T)中积累信息。
    人类习惯于从左往右、从前往后阅读,但是一段文本的内在含义取决于不同单词的排列顺序,当排列顺序固定,文本意义一般是固定的。一般来说,从右往左阅读一段文本并不会影响该文本的内在意义及对其整体含义的理解。对于RNN来说,从左往右或从右往左阅读一段文本并没有本质的区别。在实践中,将训练集中每个训练样本的单词均从右往左依次输入RNN,一般可以取得相同的效果。因此可以训练两个完全独立(不共享参数和状态向量)的RNN,一个从左往右,另一个从右往左依次读取训练样本中输入的单词。
    图二
    如图二所示,两个RNN分别输出各自状态向量,然后将二者输出的状态向量拼接,形成双向RNN的输出状态向量 y y y。状态向量 h t h_t ht h t ′ h_t^\prime ht拼接后形成的向量 [ h t , h t ′ ] [h_t, h_t^\prime] [ht,ht]可以看做双向RNN从输入文本中提取的特征向量。
    在各类时序数据处理任务中,双向RNN效果总是优于单向RNN。因为不管使用Simple RNN还是LSTM,都会或多或少遗忘掉早先的输入信息。如果RNN从左往右读取输入信息,则最后一个状态 h t h_t ht可能会遗忘掉左侧的输入信息。如果RNN从右往左读取输入信息,则最后一个状态 h t ′ h_t^\prime ht可能会遗忘掉右侧的输入信息。二者结合可使得模型不会遗忘最先读取的输入信息。
    在实际任务中,如果可以,建议使用双向RNN而不使用单向RNN,双向RNN效果至少不会比单向RNN效果差。

    4. 预训练(Pretrain)

    预训练在深度学习中非常常用,比如在训练深度卷积神经网络时,如果网络模型很大而训练集不够大,则可以先在ImageNet等大数据集上做预训练,从而使神经网络拥有比较合理的初始化,同时可以在一定程度上减少过拟合(Overfitting) 。
    训练RNN时,模型Embedding层参数数量等于【词表大小】乘以【词嵌入维度】,该层参数往往比较多,非常容易导致模型过拟合,因此可以预训练Embedding层。预训练具体过程如下:

    1. 在更大的数据集上训练一个含有Embedding层的模型
           ~~~~     - 预训练Embedding层时任务可以与原任务不一致
           ~~~~     - 预训练Embedding层时模型结构可以与原任务不一致

    两个任务越相似,预训练后Embedding层迁移效果就会越好;预训练时神经网络结构是什么都可以,甚至不用是RNN,但是必须包含Embedding层。

    1. 预训练完成后,只保留预训练阶段模型Embedding层及其参数
    2. 搭建解决实际问题的RNN模型,并在训练集上训练该RNN模型
           ~~~~     - 搭建解决实际问题的RNN模型时,Embedding层采用预训练好的Embedding层
           ~~~~     - 训练该RNN层时,如果训练集较小,建议不训练预训练阶段训练好的Embedding层参数。如果训练集相对较大,建议微调预训练阶段训练好的Embedding层参数

    5. 电影评论情感分析(四)

    改进电影评论情感分析模型,使用双层双向LSTM取代前文中单层单向LSTM。数据处理及模型训练部分均与电影评论分析(三)一致,只需更改模型搭建部分代码,稍微调整模型结构。
    使用PaddlePaddle实现多层双向LSTM非常简单,根据官方API文档paddle.nn.LSTM类包含directionnum_layers可选参数。direction表示网络迭代方向,可设置为forwardbidirect(或bidirectional),默认为forwardnum_layers表示网络层数,默认为1。实现双层双向LSTM只需在实例化paddle.nn.LSTM对象时,传入参数direction='bidirectional'num_layers=2。此外,在重写forward方法,执行前向计算流程时,需要进行相应的更改,具体代码如下:

    # -*- coding: utf-8 -*-
    # @Time    : 2021/7/6 18:55
    # @Author  : He Ruizhi
    # @File    : advanced_rnn.py
    # @Software: PyCharm
    
    import paddle
    from emb_softmax import get_data_loader
    import warnings
    warnings.filterwarnings('ignore')
    
    
    class AdvancedLSTM(paddle.nn.Layer):
        def __init__(self, embedding_dim, hidden_size):
            super(AdvancedLSTM, self).__init__()
            self.emb = paddle.nn.Embedding(num_embeddings=5149, embedding_dim=embedding_dim)
            self.lstm = paddle.nn.LSTM(input_size=embedding_dim, hidden_size=hidden_size,
                                       direction='bidirectional', num_layers=2)
            self.flatten = paddle.nn.Flatten()
            self.fc = paddle.nn.Linear(in_features=hidden_size*2, out_features=2)
            self.softmax = paddle.nn.Softmax()
    
        def forward(self, x):
            x = self.emb(x)
            # LSTM层分别返回所有时刻状态和最后时刻h与c状态,这里只使用最后时刻的h
            _, (x, _) = self.lstm(x)
            # 获取双层双向LSTM最后一层的输出状态
            x = paddle.slice(x, axes=[0], starts=[2], ends=[4])
            # 调整x的数据排列,这么处理与PaddlePaddle的LSTM层返回格式有关
            x = paddle.transpose(x, [1, 0, 2])
            x = self.flatten(x)
            x = self.fc(x)
            x = self.softmax(x)
            return x
    

    使用model.summary可查看模型结构及参数信息:

    -----------------------------------------------------------------------------------------------
     Layer (type)       Input Shape                    Output Shape                   Param #    
    ===============================================================================================
      Embedding-1        [[1, 200]]                    [1, 200, 16]                   82,384     
        LSTM-1         [[1, 200, 16]]    [[1, 200, 64], [[4, 1, 32], [4, 1, 32]]]     37,888     
       Flatten-1        [[1, 2, 32]]                     [1, 64]                         0       
       Linear-1          [[1, 64]]                        [1, 2]                        130      
       Softmax-1          [[1, 2]]                        [1, 2]                         0       
    ===============================================================================================
    Total params: 120,402
    Trainable params: 120,402
    Non-trainable params: 0
    -----------------------------------------------------------------------------------------------
    Input size (MB): 0.00
    Forward/backward pass size (MB): 0.12
    Params size (MB): 0.46
    Estimated Total Size (MB): 0.58
    -----------------------------------------------------------------------------------------------
    

    开启模型训练,打印训练过程信息:

    The loss value printed in the log is the current step, and the metric is the average value of previous steps.
    Epoch 1/5
    step 195/195 [==============================] - loss: 0.5211 - acc: 0.6451 - 47ms/step          
    Eval begin...
    step 195/195 [==============================] - loss: 0.6951 - acc: 0.7158 - 23ms/step          
    Eval samples: 24960
    Epoch 2/5
    step 195/195 [==============================] - loss: 0.2767 - acc: 0.8171 - 50ms/step          
    Eval begin...
    step 195/195 [==============================] - loss: 0.1709 - acc: 0.8181 - 24ms/step          
    Eval samples: 24960
    Epoch 3/5
    step 195/195 [==============================] - loss: 0.2327 - acc: 0.8855 - 47ms/step          
    Eval begin...
    step 195/195 [==============================] - loss: 0.2820 - acc: 0.8548 - 24ms/step          
    Eval samples: 24960
    Epoch 4/5
    step 195/195 [==============================] - loss: 0.2743 - acc: 0.9044 - 47ms/step          
    Eval begin...
    step 195/195 [==============================] - loss: 0.2730 - acc: 0.8567 - 24ms/step          
    Eval samples: 24960
    Epoch 5/5
    step 195/195 [==============================] - loss: 0.2919 - acc: 0.9254 - 47ms/step          
    Eval begin...
    step 195/195 [==============================] - loss: 0.2877 - acc: 0.8539 - 22ms/step          
    Eval samples: 24960
    

    经过实践发现,在IMDB电影评论情感分析数据集上,单层单向LSTM与双层双向LSTM结果基本一致,没有显著效果提升。回顾电影评论情感分析(一)至(四),我认为问题主要是出在Embedding层,Embedding层参数太多,训练数据集较小,出现过拟合。在此情况下,改进RNN层无法提升模型效果。在此情况下,要想提升模型效果,可以预训练Embedding层。

    6. 模型大小与训练数据集大小认识(附议)

    过拟合是深度学习实践中非常容易出现的现象,其根本原因是:

    1. 模型的复杂度大于实际问题的复杂度
    2. 模型的复杂度大于训练数据的复杂度

    在各类深度学习资料中,经常可以看到“模型太大,参数过多,训练数据集较小,模型出现过拟合”,但是几乎没有任何资料给出一个对模型和训练数据集相对大小的认识。任何人都知道训练数据越多,则可以将模型训练得越好,训练数据多多益善。但是,对于给定的存在多少参数的模型,究竟需要多少数据才能够从头训练出一套比较合理的模型参数?
    对于上述问题,其实并不存在精确的数学指导理论或证明。下面我将用一个例子,和大家一起感性理解模型大小与训练数据集大小的关系。

    假设要用数据拟合二维平面内一条直线( y = k x + b y=kx+b y=kx+b,两个参数),当训练数据只有一个,即给定平面上一个点,确定平面内一条直线。显然,在只给定一个点的情况下,拟合出来的直线有极大可能与真实直线存在较大的偏差。如果给定两个点,虽然两点可以确定一条唯一的直线,但是由于给定的两个点,是训练数据集中的随机样本,具有一定的随机性,拟合出来的直线仍有较大可能与真实直线存在一定的偏差。一般来说,当给定十数个甚至数十上百个点,才能拟合出比较精确的直线。
    图三
    从上述例子可知,比较精确地拟合只有2个参数的模型,需要约20个样本,即在模型复杂度和问题复杂度一致的情况下,训练出一个比较精确合理的模型,训练集数据量预计要十倍于模型参数数量。
    在深度学习实践中,模型复杂度很有可能大于实际问题复杂度,而且问题和数据特征空间维度可达成百上千甚至数百万维。模型复杂度比实际问题复杂度越大,则模型越容易拟合训练数据中的噪声、异常值等不能反映实际问题客观规律的随机误差,模型需要更多数据才能学到实际问题中的真实规律。问题和数据特征空间维度越高,则求解空间越大,相当于可选答案更多,干扰项越多,需要更多信息才能找到真实规律。因此,训练深度学习模型,训练集数据量哪怕百倍千倍于模型参数量,都无法肯定的说训练数据集已经足够大。
    深度学习模型参数动辄数十万上百万,OpenAI出品的GPT-3模型参数达到了令人恐怖的1750亿,Google出品的Switch Transformer语言模型参数达到了令人发指的1.6万亿,快手出品的精排排序模型参数据说达到了丧心病狂的1.9万亿。
    在深度学习领域,训练数据集不论多大,永远都可以说——两个怎么够?我要二十个!
    图四

    7. 参考资料链接

    1. 九品芝麻官(普通话版)
    2. https://www.youtube.com/watch?v=pzWHk_M23a0&list=PLvOO0btloRnuTUGN4XqO85eKPeFSZsEqK&index=5&t=608s
    3. https://www.icourse163.org/learn/ZJU-1206573810?tid=1206902211#/learn/content?type=detail&id=1234658158&cid=1254264368&replay=true
    展开全文
  • 文章目录基本结构实战—单向RNN实战—双向RNN实战—Attention+RNN 基本结构 RNN常见的结构如下: 其中的单元AAA可以是全连接RNN,LSTM,GRU。 tensorfow2.0中将这三个封装到以下接口中: keras.layers.SimpleRNN ...
  • 双向LSTM (双向RNN)

    千次阅读 2020-08-24 11:38:17
    单向的 RNN,是根据前面的信息推出后面的,但有时候只看前面的词是不够的, 例如, 我今天不舒服,我打算____一天。 只根据‘不舒服‘,可能推出我打算‘去医院‘,‘睡觉‘,‘请假‘等等,但如果加上后面的‘一...
  • https://cloud.tencent.com/developer/article/1144238添加链接描述
  • BiLSTM+CRF (一)双向RNN 浅谈

    千次阅读 2018-10-28 16:57:01
    为什么要使用双向RNN? 一般的按序列顺序过来的RNN会记录、保存来自前面序列的信息,这些历史信息对当前的输出是很有帮助的。但是有些问题,序列当前位置历史信息和这个位置未来的信息会共同对计算当前位置的输出有...
  • 变长双向rnn的正确使用姿势

    千次阅读 2018-01-02 19:56:56
    变长双向rnn的正确使用姿势在《深度学习之TensorFlow入门、原理与进阶实战》一书的9.4.2中的第4小节中,介绍过变长动态RNN的实现。这里在来延伸的讲解一下双向动态rnn在处理变长序列时的应用。其实双向RNN的使用中,...
  • 双向RNN模型如下: 用公式表示双向RNN过程如下: 另外,双向RNN需要保存两个方向的权重矩阵,所以需要的内存约为RNN的两倍。 三、深层RNN(DRNN)网络结构 深层RNN网络是在RNN模型多了几个隐藏层,是因为考虑到当信息...
  • 同样的,我们也可以在双向RNN模型基础上加多几层隐藏层得到深层双向RNN模型。 注:每一层循环体中参数是共享的,但是不同层之间的权重矩阵是不同的。 四、Keras对RNN的支持 在Keras同样对RNN模型进行...
  • 再话RNN,LSTM(双向RNN) 之前写了一篇关于RNN,LSTM,GRU的公式推导以及前向传播的文章,但是后来发现,当时自己写的时候挺清楚的,后来过段时间就忘了,看来还是理解的不够啊。所以今天这篇文章写一下,到底什么是...
  • 1.使用单向RNN 建立输入层,RNN层和输出层 n_steps * n_inputs = 28 * 28,读取的单位是图片中的一行像素 输入数据:x=[batch_size,n_steps,n_inputs] 输出数据:y=[batch_size,n_classes] 输入层: 输入数据:x=...
  • 双向RNN理解笔记

    2018-09-03 19:46:00
    双向RNN需要的内存是单向RNN的两倍,因为在同一时间点,双向RNN需要保存两个方向上的权重参数,在分类的时候,需要同时输入两个隐藏层输出的信息。 举例表示 : 程序表示 : n是非常相似的. 定义前向和...
  • 双向RNN】的理解

    千次阅读 2018-11-07 17:20:19
    双向RNN使用的场景:有些情况下,当前的输出不只依赖于之前的序列元素,还可能依赖之后的序列元素; 比如做完形填空,机器翻译等应用。 Tensorflow 中实现双向RNN 的API是:bidirectional_dynamic_rnn; 其本质主要...
  • 基于注意力的双向RNN文本分类的Tensorflow实现。 (以朴素的双向RNN模型为基准) 要求 的Python 3 张量流 点安装-r requirements.txt 用法 准备数据 我们使用的是预处理版本。 要使用样本数据(100K火车/ 30K测试)...
  • optimizer = torch.optim.Adam(rnn.parameters(),lr=learning_rate) #Train the Model for epoch in range(num_epochs): for i,(images,labels) in enumerate(train_loader): images = Variable(images.view(-1,...
  • 今天给大家介绍的是被誉为“欧陆第一...作者受双向RNN和SMILES本身的结构特性启发,提出一种可用于SMILES生成和数据增强的新的双向RNN分子生成模型——BIMODAL。该模型通过交替学习进行双向分子设计,并且该模型与...
  • 双向RNN&Deep RNN

    千次阅读 2019-03-30 13:28:20
    双向RNN Bidirectional RNN(双向RNN)假设当前t的输出不仅仅和之前的序列有关,并且 还与之后的序列有关,例如:预测一个语句中缺失的词语那么需要根据上下文进 行预测;Bidirectional RNN是一个相对简单的RNNs,由...
  • def my_lstm_layer(input_reps, lstm_dim=int(768 / 2), input_lengths=None, scope_name="my_rnn", reuse=False, is_training=True, dropout_rate=0.2, use_cudnn=False): ''' input_reps: [batch_size, seq_...
  • 目录 前置知识 循环神经网络(RNN) 文本向量化 RNN 建模 RNN 模型改进 LSTM(Long Short Term Memory) LSTM变形与数学表达式 LSTM变形与数学表达式 门控循环单元GRU(Grated Recurrent Unit) 双向RNN模型 前置...
  • 双向RNN与LSTM模块相结合可以显著提高你的性能,当你将其与注意机制相结合时,你将获得机器翻译、情绪分析等用例的最新性能。希望本文对你有所帮助。里面有很多数学方程,我希望不会太吓人。如果你还有什么疑问,...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 10,899
精华内容 4,359
关键字:

双向rnn