手推反向传播+numpy实现
反向传播的重要性不必多说,手推也是必备基础,大厂面试要求用numpy实现一下BP也是经常的事。下面以一个简单的两层网络为例(简单到连bias都没有的那种),真·手推反向传播+numpy实现。
说明:
input:输入
net_h:隐层
S(x):sigmoid简写
SD(x):sigmoid导数的简写
out_h:隐层经过sigmoid激活的输出
net_o:输出层
out_o:经过经过sigmoid激活的输出层,也就是最后的输出
target(简写t1、t2):Ground Truth
L:损失函数,一个简单的MSE
gw:L在w的偏导数
下面是代码:
1.对以上手推图片的实现:
import numpy as npdef sigmoid(x):return 1 / (1 + np.exp(-x))
def sigmoid_derivationx(y):return y * (1 - y)
def back():input = np.array([0.9, 0.1], dtype='float')weight_1 = np.array([[0.15, 0.20], [0.25, 0.30]], dtype='float')weight_2 = np.array([[0.40, 0.45], [0.50, 0.55]], dtype='float')target_output = np.array([0.11, 0.89], dtype='float')learning_rate = 0.5steps = 1000while steps > 0:steps -= 1# 正向传播# layer-1net_h1, net_h2 = np.dot(input, weight_1) # 第一层的计算结果out_h1, out_h2 = [1 / (1 + np.exp(-net_h1)), 1 / (1 + np.exp(-net_h2))] # sigmoid激活后的输出# layer-2layer_2_input = np.array([out_h1, out_h2], dtype='float')net_o1, net_o2 = np.dot(layer_2_input, weight_2) # 第二层的计算结果out_o1, out_o2 = [1 / (1 + np.exp(-net_o1)), 1 / (1 + np.exp(-net_o2))] # sigmoid激活后的输出# 计算梯度,反向传播total_loss = sum([pow(target_output-real_output, 2)/2 for target_output, real_output in zip(target_output, [out_o1, out_o2])])print('网络的输出:step:%d loss=%f out_o1=%f out_o2=%f ' % (steps, total_loss, out_o1, out_o2))# gradient for layer-2gradient_w5 = -1 * (target_output[0] - out_o1) * out_o1 * (1 - out_o1) * out_h1gradient_w6 = -1 * (target_output[0] - out_o1) * out_o1 * (1 - out_o1) * out_h2gradient_w7 = -1 * (target_output[1] - out_o2) * out_o2 * (1 - out_o2) * out_h1gradient_w8 = -1 * (target_output[1] - out_o2) * out_o2 * (1 - out_o2) * out_h2# gradient for layer-1gradient_w1 = -1 * (target_output[0] - out_o1) * out_o1 * (1 - out_o1) * weight_2[0][0] * out_h1 * \(1 - out_h1)*input[0] - (target_output[1] - out_o2) * out_o2 * (1 - out_o2) * weight_2[1][0] * \out_h1 * (1 - out_h1)*input[0]gradient_w2 = -1 * (target_output[0] - out_o1) * out_o1 * (1 - out_o1) * weight_2[0][0] * out_h1 * \(1 - out_h1) * input[1] - (target_output[1] - out_o2) * out_o2 * (1 - out_o2) * weight_2[1][0] * \out_h1 * (1 - out_h1)*input[1]gradient_w3 = -1 * (target_output[0] - out_o1) * out_o1 * (1 - out_o1) * weight_2[0][1] * out_h2 * \(1 - out_h2) * input[0] - (target_output[1] - out_o2) * out_o2 * (1 - out_o2) * weight_2[1][1] * \out_h2 * (1 - out_h2)*input[0]gradient_w4 = -1 * (target_output[0] - out_o1) * out_o1 * (1 - out_o1) * weight_2[0][1] * out_h2 * \(1 - out_h2) * input[1] - (target_output[1] - out_o2) * out_o2 * (1 - out_o2) * weight_2[1][1] * \out_h2 * (1 - out_h2)*input[1]# update weight# layer -1weight_1[0][0] = weight_1[0][0] - learning_rate * gradient_w1weight_1[1][0] = weight_1[1][0] - learning_rate * gradient_w2weight_1[0][1] = weight_1[0][1] - learning_rate * gradient_w3weight_1[1][1] = weight_1[1][1] - learning_rate * gradient_w4
back()
2.用矩阵相乘实现:
import numpy as npdef sigmoid(x):return 1 / (1 + np.exp(-x))
def sigmoid_derivationx(y):return y * (1 - y)
def back_matrix():input = np.array([0.9, 0.1], dtype='float')weight_1 = np.array([[0.5, 0.5],[0.5, 0.5]], dtype='float')weight_2 = np.array([[0.5, 0.5],[0.5, 0.5]], dtype='float')target_output = np.array([0.11, 0.89], dtype='float')learning_rate = 0.5steps = 1000while steps > 0:steps -= 1# 正向传播# layer-1net_h = np.dot(input, weight_1) # 第一层的计算结果out_h = sigmoid(net_h) # sigmoid激活后的输出# layer-2layer_2_input = np.array(out_h, dtype='float')net_o = np.dot(layer_2_input, weight_2) # 第二层的计算结果out_o = sigmoid(net_o) # sigmoid激活后的输出# 计算梯度,反向传播total_loss = sum([pow(target_output-real_output, 2)/2 for target_output, real_output in zip(target_output, out_o)])print('网络的输出:step:%d loss=%f out_o1=%f out_o2=%f ' % (steps, total_loss, out_o[0], out_o[0]))gradient_weight_2 = np.zeros_like(weight_2)for i in range(gradient_weight_2.shape[1]):gradient_weight_2[:, i] = (out_o[i] - target_output[i]) * sigmoid_derivationx(out_o[i]) * out_hgradient_weight_1 = np.zeros_like(weight_1)for i in range(gradient_weight_1.shape[1]):dot1 = -1 * (target_output - out_o) * out_o * sigmoid_derivationx(out_h)dot2 = np.reshape(weight_2[:, i], (-1, 1))gradient_weight_1[:, i] = np.dot([dot1], dot2) * input# update weight# layer -1weight_1 = weight_1 - learning_rate * gradient_weight_1# layer-2weight_2 = weight_2 - learning_rate * gradient_weight_2if steps == 1:print('网络的输出:loss=%f out_o1=%f out_o2=%f ' % (total_loss, out_o[0], out_o[1]))break
back_matrix()
手推反向传播+numpy实现相关推荐
- 学习笔记三:MLP基本原理、矩阵求导术推反向传播、激活函数、Xavier
文章目录 一.BP神经网络(MLP) 1.1 感知机模型及其局限性 1.2 BP神经网络基本原理 1.3 softmax多分类.求导 1.4 二分类使用softmax还是sigmoid好? 1.5 为 ...
- ztree在刷新时第一个父节点消失_从反向传播推导到梯度消失and爆炸的原因及解决方案(从DNN到RNN,内附详细反向传播公式推导)...
引言:参加了一家公司的面试和另一家公司的笔试,都问到了这个题!看来很有必要好好准备一下,自己动手推了公式,果然理解更深入了!持续准备面试中... 一. 概述: 想要真正了解梯度爆炸和消失问题,必须手推 ...
- 误差反向传播法实现手写数字识别(纯numpy实现)
前面一篇博客中我们讲解了仅仅使用numpy实现了数值微分法的梯度下降完成手写数字识别,使用数值微分的计算量会非常大,因此耗时也非常久.在这里我们使用另外一种快速计算梯度的方式-误差反向传播法. 代码如 ...
- (二十四) 手推BP神经网络的前向传播和反向传播
手推BP神经网络的前向传播和反向传播 一.基本术语 1.监督学习与非监督学习 Supervised Learning有监督式学习: 输入的数据被称为训练数据,一个模型需要通过一个训练过程,在这个过程中 ...
- 深度学习笔记--pytorch从梯度下降到反向传播BP到线性回归实现,以及API调用和手写数据集的实现
梯度下降和反向传播 目标 知道什么是梯度下降 知道什么是反向传播 1. 梯度是什么? 梯度:是一个向量,导数+变化最快的方向(学习的前进方向) 回顾机器学习 收集数据 x x x ,构建机器学习模型 ...
- 仅使用numpy从头开始实现神经网络,包括反向传播公式推导过程
仅使用numpy从头开始实现神经网络,包括反向传播公式推导过程: https://www.ctolib.com/yizt-numpy_neural_network.html
- numpy实现简单的二层网络------前向和反向传播
会推导神经网络的前向和反向传播是深度学习的基础,也许大家在实验使用Tensorflow框架,只需要调用某一个损失函数,传入参数就可以得到损失,或者Mxnet框架,你都不需要调用任何函数,给个标志就可以 ...
- 手写 单隐藏层神经网络_反向传播(Matlab实现)
文章目录 要点 待优化 效果 代码 mian train_neural_net 待优化(1)已完成 要点 1.sigmoid函数做为激活函数,二分类交叉熵函数做损失函数 2.可以同时对整个训练集进行训 ...
- 手撕CNN神经网络(二)反向传播(back propagation)
反向传播简单来说就是通过求偏导数从而更新神经网络中权重w的过程 首先先简单复习一下前向传播(forward propagation) 篇幅有限,bias(b)在图中就没画出来,大家知道有这么个东西就好 ...
最新文章
- mysql查看当前实时连接数
- 解决Eclipse 启动后总是Building WorkSpace(sleeping)
- 前端学习(1965)vue之电商管理系统电商系统之渲染添加参数的按钮
- Windows系统安全从定制IP策略开始
- llinux文本三剑客之grep、egrep及相应的正则表达式和用法
- 【matplotlib笔记】柱形图、直方图、散点图、饼图以及叠加图绘制
- 一个 Accept-Encoding 引发的 requests 爬虫乱码问题
- 统计学习方法第15章-奇异值分解SVD
- 「模拟赛20180306」回忆树 memory LCA+KMP+AC自动机+树状数组
- OpenGL基础54:点光源阴影
- Linux shell 中的那些你值得一试的小把戏
- java response 输出word_java导出数据到word(一)
- yolo v3 的keras 版本(转载)
- win10微软图标点击无反应_Win10任务栏系统图标点击无反应的解决方法
- linux下安装java
- WiFi产品的一般射频电路设计
- 字母数字下划线常用正则表达式
- 楼下邻居是事逼怎么办
- Good Numbers (hard version)cf#595(Div.3)
- purifier用来过滤危险的标签xss