热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

递归神经网络部分组件(七)

递归神经网络的基础知识参考:https:www.zybuluo.comhanbingtaonote626300自然语言和自然场景解析在自然语言处理任务中ÿ

递归神经网络的基础知识参考:
https://www.zybuluo.com/hanbingtao/note/626300

自然语言和自然场景解析


  • 在自然语言处理任务中,如果我们能够实现一个解析器,将自然语言解析为语法树,那么毫无疑问,这将大大提升我们对自然语言的处理能力。而递归神经网络就能够完成句子的语法分析,并产生一个语法解析树。
  • 除了自然语言之外,自然场景也具有可组合的性质。因此,我们可以用类似的模型完成自然场景的解析

下面是代码实现:
代码中涉及的公式推导参考上面的连接。

activator.py

#!/usr/bin/env python
# -*- coding: UTF-8 -*-import numpy as npclass ReluActivator(object):def forward(self, weighted_input):#return weighted_inputreturn max(0, weighted_input)def backward(self, output):return 1 if output > 0 else 0class IdentityActivator(object):def forward(self, weighted_input):return weighted_inputdef backward(self, output):return 1class SigmoidActivator(object):def forward(self, weighted_input):return 1.0 / (1.0 + np.exp(-weighted_input))def backward(self, output):return output * (1 - output)class TanhActivator(object):def forward(self, weighted_input):return 2.0 / (1.0 + np.exp(-2 * weighted_input)) - 1.0def backward(self, output):return 1 - output * output

递归神经网络部分组件实现部分:

# -*- coding: UTF-8 -*-import numpy as np
from activators import IdentityActivator# 用它保存递归神经网络生成的整棵树,用来构造父和子的关系
class TreeNode(object):def __init__(self, data, children=[], children_data=[]):self.parent = Noneself.children = childrenself.children_data = children_dataself.data = datafor child in children: # 设定子节点的父类child.parent = self #print 'here:',child.parent# 递归神经网络实现
class RecursiveLayer(object):def __init__(self, node_width, child_count, activator, learning_rate):'''递归神经网络构造函数node_width: 表示每个节点的向量的维度child_count: 每个父节点有几个子节点activator: 激活函数对象learning_rate: 梯度下降算法学习率'''self.node_width = node_widthself.child_count = child_countself.activator = activatorself.learning_rate = learning_rate# 权重数组Wself.W = np.random.uniform(-1e-4, 1e-4,(node_width, node_width * child_count))# 偏置项bself.b = np.zeros((node_width, 1))# 递归神经网络生成的树的根节点self.root = Nonedef forward(self, *children): # 可变参数的用法参考https://blog.csdn.net/lilong117194/article/details/80091217'''前向计算'''children_data = self.concatenate(children)#print 'children_data:', children_dataparent_data = self.activator.forward(np.dot(self.W, children_data) + self.b)#print 'parent_data:',parent_dataprint 'children:',childrenself.root = TreeNode(parent_data, children, children_data)print 'tt..',self.rootprint 'self.root.children:',self.root.childrendef backward(self, parent_delta):'''BPTS反向传播算法'''self.calc_delta(parent_delta, self.root)self.W_grad, self.b_grad = self.calc_gradient(self.root)def update(self):'''使用SGD算法更新权重'''self.W -= self.learning_rate * self.W_gradself.b -= self.learning_rate * self.b_graddef reset_state(self):self.root = Nonedef concatenate(self, tree_nodes):'''将各个树节点中的数据拼接成一个长向量'''concat = np.zeros((0,1))for node in tree_nodes:concat = np.concatenate((concat, node.data))#print 'concat:',concatreturn concat# 这里是难点def calc_delta(self, parent_delta, parent):'''计算每个节点的delta'''parent.delta = parent_deltaif parent.children:# 根据式2计算每个子节点的delta(只是下一层的)children_delta = np.dot(self.W.T, parent_delta) * (self.activator.backward(parent.children_data))print 'children_delta——>',children_delta# slices = [(子节点编号,子节点delta起始位置,子节点delta结束位置)]slices = [(i, i * self.node_width, (i + 1) * self.node_width)for i in range(self.child_count)]print 'slices:',slices# 针对每个子节点,递归调用calc_delta函数for s in slices:print 'children_delta[s[1]:s[2]]:',children_delta[s[1]:s[2]]print 'parent.children[s[0]]):',parent.children[s[0]]self.calc_delta(children_delta[s[1]:s[2]], parent.children[s[0]])def calc_gradient(self, parent):'''计算每个节点权重的梯度,并将它们求和,得到最终的梯度'''W_grad = np.zeros((self.node_width, self.node_width * self.child_count))b_grad = np.zeros((self.node_width, 1))if not parent.children:return W_grad, b_gradparent.W_grad = np.dot(parent.delta, parent.children_data.T)parent.b_grad = parent.deltaW_grad += parent.W_gradb_grad += parent.b_gradfor child in parent.children:W, b = self.calc_gradient(child)W_grad += Wb_grad += breturn W_grad, b_grad# 打印输出def dump(self, **kwArgs):print 'root.data: %s' % self.root.dataprint 'root.children_data: %s' % self.root.children_dataif kwArgs.has_key('dump_grad'):print 'W_grad: %s' % self.W_gradprint 'b_grad: %s' % self.b_graddef data_set():children = [TreeNode(np.array([[1],[2]])),TreeNode(np.array([[3],[4]])),TreeNode(np.array([[5],[6]]))]d = np.array([[0.5],[0.8]])return children, ddef gradient_check():'''梯度检查'''# 设计一个误差函数,取所有节点输出项之和error_function = lambda o: o.sum()rnn = RecursiveLayer(2, 2, IdentityActivator(), 1e-3)# 计算forward值x, d = data_set()rnn.forward(x[0], x[1])rnn.forward(rnn.root, x[2])# 求取sensitivity mapsensitivity_array = np.ones((rnn.node_width, 1),dtype=np.float64)# 计算梯度rnn.backward(sensitivity_array)# 检查梯度epsilon = 10e-4for i in range(rnn.W.shape[0]):for j in range(rnn.W.shape[1]):rnn.W[i,j] += epsilonrnn.reset_state()rnn.forward(x[0], x[1])rnn.forward(rnn.root, x[2])err1 = error_function(rnn.root.data)rnn.W[i,j] -= 2*epsilonrnn.reset_state()rnn.forward(x[0], x[1])rnn.forward(rnn.root, x[2])err2 = error_function(rnn.root.data)expect_grad = (err1 - err2) / (2 * epsilon)rnn.W[i,j] += epsilonprint 'weights(%d,%d): expected - actural %.4e - %.4e' % (i, j, expect_grad, rnn.W_grad[i,j])return rnndef test():children, d = data_set()# node_width, child_count, activator, learning_raternn = RecursiveLayer(2, 2, IdentityActivator(), 1e-3)rnn.forward(children[0], children[1])rnn.dump() # 打印输出父子节点的关系和datarnn.forward(rnn.root, children[2])rnn.dump()rnn.backward(d)rnn.dump(dump_grad='true')return rnntest()

运行结果:

children: (<__main__.TreeNode object at 0x000000000BA4BF60>, <__main__.TreeNode object at 0x000000000BA4BD68>)
tt.. <__main__.TreeNode object at 0x000000000BA5E400>
self.root.children: (<__main__.TreeNode object at 0x000000000BA4BF60>, <__main__.TreeNode object at 0x000000000BA4BD68>)
root.data: [[ 8.10365462e-05][ -1.20068464e-06]]
root.children_data: [[ 1.][ 2.][ 3.][ 4.]]
children: (<__main__.TreeNode object at 0x000000000BA5E400>, <__main__.TreeNode object at 0x000000000BA4BC88>)
tt.. <__main__.TreeNode object at 0x000000000BAA6358>
self.root.children: (<__main__.TreeNode object at 0x000000000BA5E400>, <__main__.TreeNode object at 0x000000000BA4BC88>)
root.data: [[ 8.67226403e-05][ -2.18991385e-04]]
root.children_data: [[ 8.10365462e-05][ -1.20068464e-06][ 5.00000000e&#43;00][ 6.00000000e&#43;00]]
children_delta——> [[ -3.40659777e-05][ 7.72187116e-05][ -2.12167087e-05][ -4.29089851e-06]]
slices: [(0, 0, 2), (1, 2, 4)]
children_delta[s[1]:s[2]]: [[ -3.40659777e-05][ 7.72187116e-05]]
parent.children[s[0]]): <__main__.TreeNode object at 0x000000000BA5E400>
children_delta——> [[ -2.03214060e-09][ 4.49859993e-09][ -1.02736169e-08][ 5.25062172e-09]]
slices: [(0, 0, 2), (1, 2, 4)]
children_delta[s[1]:s[2]]: [[ -2.03214060e-09][ 4.49859993e-09]]
parent.children[s[0]]): <__main__.TreeNode object at 0x000000000BA4BF60>
children_delta[s[1]:s[2]]: [[ -1.02736169e-08][ 5.25062172e-09]]
parent.children[s[0]]): <__main__.TreeNode object at 0x000000000BA4BD68>
children_delta[s[1]:s[2]]: [[ -2.12167087e-05][ -4.29089851e-06]]
parent.children[s[0]]): <__main__.TreeNode object at 0x000000000BA4BC88>
root.data: [[ 8.67226403e-05][ -2.18991385e-04]]
root.children_data: [[ 8.10365462e-05][ -1.20068464e-06][ 5.00000000e&#43;00][ 6.00000000e&#43;00]]
W_grad: [[ 6.45229542e-06 -6.87322977e-05 2.49989780e&#43;00 2.99986374e&#43;00][ 1.42047949e-04 1.53476876e-04 4.00023166e&#43;00 4.80030887e&#43;00]]
b_grad: [[ 0.49996593][ 0.80007722]]

代码中做了一些打印输出&#xff0c;以便于理解代码。

这里要注意几点&#xff1a;


  • 由于权重是在所有层共享的&#xff0c;所以和循环神经网络一样&#xff0c;递归神经网络的最终的权重梯度是各个层权重梯度之和。
  • 网络的树构建大概是这样的&#xff1a;
    这里写图片描述
    具体的实现流程还要看代码。
  • 这里没有进行梯度检查&#xff0c;但在上一篇lstm中实现过&#xff0c;这里的原理都是一样的。
  • 整个代码架构的搭建是难点

通过初步学习递归神经网络的实现和应用场景&#xff0c;感觉递归神经网络很神奇&#xff0c;期待进一步的深入学习。


推荐阅读
  • 不同优化算法的比较分析及实验验证
    本文介绍了神经网络优化中常用的优化方法,包括学习率调整和梯度估计修正,并通过实验验证了不同优化算法的效果。实验结果表明,Adam算法在综合考虑学习率调整和梯度估计修正方面表现较好。该研究对于优化神经网络的训练过程具有指导意义。 ... [详细]
  • 本文详细解析了JavaScript中相称性推断的知识点,包括严厉相称和宽松相称的区别,以及范例转换的规则。针对不同类型的范例值,如差别范例值、统一类的原始范例值和统一类的复合范例值,都给出了具体的比较方法。对于宽松相称的情况,也解释了原始范例值和对象之间的比较规则。通过本文的学习,读者可以更好地理解JavaScript中相称性推断的概念和应用。 ... [详细]
  • YOLOv7基于自己的数据集从零构建模型完整训练、推理计算超详细教程
    本文介绍了关于人工智能、神经网络和深度学习的知识点,并提供了YOLOv7基于自己的数据集从零构建模型完整训练、推理计算的详细教程。文章还提到了郑州最低生活保障的话题。对于从事目标检测任务的人来说,YOLO是一个熟悉的模型。文章还提到了yolov4和yolov6的相关内容,以及选择模型的优化思路。 ... [详细]
  • Java容器中的compareto方法排序原理解析
    本文从源码解析Java容器中的compareto方法的排序原理,讲解了在使用数组存储数据时的限制以及存储效率的问题。同时提到了Redis的五大数据结构和list、set等知识点,回忆了作者大学时代的Java学习经历。文章以作者做的思维导图作为目录,展示了整个讲解过程。 ... [详细]
  • 浏览器中的异常检测算法及其在深度学习中的应用
    本文介绍了在浏览器中进行异常检测的算法,包括统计学方法和机器学习方法,并探讨了异常检测在深度学习中的应用。异常检测在金融领域的信用卡欺诈、企业安全领域的非法入侵、IT运维中的设备维护时间点预测等方面具有广泛的应用。通过使用TensorFlow.js进行异常检测,可以实现对单变量和多变量异常的检测。统计学方法通过估计数据的分布概率来计算数据点的异常概率,而机器学习方法则通过训练数据来建立异常检测模型。 ... [详细]
  • 本文介绍了在Python张量流中使用make_merged_spec()方法合并设备规格对象的方法和语法,以及参数和返回值的说明,并提供了一个示例代码。 ... [详细]
  • Learning to Paint with Model-based Deep Reinforcement Learning
    本文介绍了一种基于模型的深度强化学习方法,通过结合神经渲染器,教机器像人类画家一样进行绘画。该方法能够生成笔画的坐标点、半径、透明度、颜色值等,以生成类似于给定目标图像的绘画。文章还讨论了该方法面临的挑战,包括绘制纹理丰富的图像等。通过对比实验的结果,作者证明了基于模型的深度强化学习方法相对于基于模型的DDPG和模型无关的DDPG方法的优势。该研究对于深度强化学习在绘画领域的应用具有重要意义。 ... [详细]
  • 目录实现效果:实现环境实现方法一:基本思路主要代码JavaScript代码总结方法二主要代码总结方法三基本思路主要代码JavaScriptHTML总结实 ... [详细]
  • javascript  – 概述在Firefox上无法正常工作
    我试图提出一些自定义大纲,以达到一些Web可访问性建议.但我不能用Firefox制作.这就是它在Chrome上的外观:而那个图标实际上是一个锚点.在Firefox上,它只概述了整个 ... [详细]
  • 使用Ubuntu中的Python获取浏览器历史记录原文: ... [详细]
  • 无损压缩算法专题——LZSS算法实现
    本文介绍了基于无损压缩算法专题的LZSS算法实现。通过Python和C两种语言的代码实现了对任意文件的压缩和解压功能。详细介绍了LZSS算法的原理和实现过程,以及代码中的注释。 ... [详细]
  • sklearn数据集库中的常用数据集类型介绍
    本文介绍了sklearn数据集库中常用的数据集类型,包括玩具数据集和样本生成器。其中详细介绍了波士顿房价数据集,包含了波士顿506处房屋的13种不同特征以及房屋价格,适用于回归任务。 ... [详细]
  • 本文详细介绍了Java中vector的使用方法和相关知识,包括vector类的功能、构造方法和使用注意事项。通过使用vector类,可以方便地实现动态数组的功能,并且可以随意插入不同类型的对象,进行查找、插入和删除操作。这篇文章对于需要频繁进行查找、插入和删除操作的情况下,使用vector类是一个很好的选择。 ... [详细]
  • 热血合击脚本辅助工具及随机数生成器源码分享
    本文分享了一个热血合击脚本辅助工具及随机数生成器源码。游戏脚本能够实现类似真实玩家的操作,但信息量有限且操作不可控。热血合击脚本辅助工具可以帮助玩家自动刷图、换图拉怪等操作,并提供了雷电云手机的扩展服务。此外,还介绍了使用mt_rand函数作为随机数生成器的代码示例。 ... [详细]
  • [大整数乘法] java代码实现
    本文介绍了使用java代码实现大整数乘法的过程,同时也涉及到大整数加法和大整数减法的计算方法。通过分治算法来提高计算效率,并对算法的时间复杂度进行了研究。详细代码实现请参考文章链接。 ... [详细]
author-avatar
手机用户2602889575
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有