【Python机器学习】神经网络中误差反向传播(BP)算法详解及代码示例(图文解释 附源码)

简介: 【Python机器学习】神经网络中误差反向传播(BP)算法详解及代码示例(图文解释 附源码)

需要全部代码请点赞关注收藏后评论留言私信~~~

误差反向传播学习算法

用神经网络来完成机器学习任务,先要设计好网络结构S,然后用训练样本去学习网络中的连接系数和阈值系数,即网络参数S,最后才能用来对测试样本进行预测。

在研究早期,没有适合多层神经网络的有效的参数学习方法是长期困扰该领域研究者的关键问题,以致于人们对人工神经网络的前途产生了怀疑,导致该领域的研究进入了低谷期。直到1986年,以Rumelhart和McCelland为首的小组发表了误差反向传播(Error Back Propagation,BP)算法,该问题才得以解决,多层神经网络从此得到快速发展。

采用BP算法来学习的、无反馈的、同层节点无连接的、多层结构的前馈神经网络称为BP神经网络。

逻辑代数中的异或运算时非线性的,它不能由单个神经元来模拟,下面用模拟异或运算的神经网络为例来说明BP学习过程

样本:

网络结构:      

要学习的参数:

BP学习算法可分为前向传播预测与反向传播学习两个过程。

为了方便求导,隐层和输出层的激励函数采用Sigmoid函数:

Sigmoid函数的导数为:

前向传播预测过程

设网络各参数初值为:

取第一个训练样本(0,0),第1隐层的输出:

用l^(1)和l^(2)表示标签值,采用各标签值的均方误差MSE作为总误差,并将总误差依次展开至输入层:

可见,总误差E是各层参数变量的函数,因此学习的目的就是通过调整各参数变量的值,使E最小。可采用梯度下降法求解。

第一个训练样本的标签值为(0,1),因此,输出产生的误差分别为0.743和−0.236。总误差:E=1/2∑_i=1^2▒(z^(i)−l^(i))^2=0.304 输出层节点的参数更新,以节点1的w_2^(1,1)和θ_2^(1)为例详细讨论。

先求偏导∂E/∂w_2^(1,1):∂E/∂w_2^(1,1)=∂E/∂y_2^(1)∙∂y_2^(1)/∂w_2^(1,1)=∂[1/2∑_i=1^2▒(y_2^(i)−l^(i))^2]/∂y_2^(1)∙∂y_2^(1)/∂w_2^(1,1)=(y_2^(1)−l^(1))∙∂y_2^(1)/∂w_2^(1,1)

式中括号(y_2^(1)−l^(1))是输出层节点1的校对误差,记为E_2^1,即E_2^1=y_2^(1)−l^(1)=0.743。因此∂E/∂w_2^(1,1)可视为该节点的校对误差乘以该节点输出对待更新参数变量的偏导:∂E/∂w_2^(1,1)=E_2^1∙∂y_2^(1)/∂w_2^(1,1)

后面求导过程过于繁杂 此处省略不表

以上给出了输入第一个训练样本后,网络的前向预测和反向学习过程。可将样本依次输入网络进行训练。一般要进行多轮训练。

运行输出结果如下

经过2000轮训练,每轮平均值总误差由0.32降维0.008

最后一轮的四个输出与相应标签值对比为下 预测输出十分接近实际标签值

部分代码如下

for j in range(2000):
    print("\n\n轮:", j)
    E = 0.0
    for i in range(4):
        print("样本:", i)
        print("实例:", XX[i])
        print("标签", L[i])
        ### 前向传播预测
        # 计算第1隐层的输出
        Y1[0] = y_1_1(W1, theta1, XX[i])
        Y1[1] = y_1_2(W1, theta1, XX[i])
        #print("第1隐层的输出:", Y1)
        # 计算第2隐层的输出
        Y2[0] = y_2_1(W2, theta2, Y1)
        Y2[1] = y_2_2(W2, theta2, Y1)
        print("第2隐层的输出:", Y2)
        ### 后向传播误差
        # 计算第2隐层的校对误差
        E2[0] = Y2[0] - L[i][0]
        E2[1] = Y2[1] - L[i][1]
        E += 0.5*(E2[0]*E2[0]+E2[1]*E2[1])
        #print("总误差", E)
        #print("第2隐层的校对误差", E2)
        # 计算第1隐层的校对误差
        E1[0] = E2[0]*Y2[0]*(1 - Y2[0])*W2[0,0] + E2[1]*Y2[1]*(1 - Y2[1])*W2[0,1]
        E1[1] = E2[0]*Y2[0]*(1 - Y2[0])*W2[1,0] + E2[1]*Y2[1]*(1 - Y2[1])*W2[1,1]
        #print("第1隐层的校对误差", E1)
        ### 更新系数
        # 更新第2隐层的系数
        W2[0,0] = W2[0,0] - a*E2[0]*Y2[0]*(1 - Y2[0])*Y1[0]
        W2[1,0] = W2[1,0] - a*E2[0]*Y2[0]*(1 - Y2[0])*Y1[1]
        theta2[0] = theta2[0] - a*E2[0]*Y2[0]*(1 - Y2[0])
        W2[0,1] = W2[0,1] - a*E2[1]*Y2[1]*(1 - Y2[1])*Y1[0]
        W2[1,1] = W2[1,1] - a*E2[1]*Y2[1]*(1 - Y2[1])*Y1[1]
        theta2[1] = theta2[1] - a*E2[1]*Y2[1]*(1 - Y2[1])
        #print("第2隐层的连接系数", W2)
        #print("第2隐层的阈值系数", theta2)
        # 更新第1隐层的系数
        W1[0,0] = W1[0,0] - a*E1[0]*Y1[0]*(1 - Y1[0])*XX[i][0]
        W1[1,0] = W1[1,0] - a*E1[0]*Y1[0]*(1 - Y1[0])*XX[i][1]
        theta1[0] = theta1[0] - a*E1[0]*Y1[0]*(1 - Y1[0])
        W1[0,1] = W1[0,1] - a*E1[1]*Y1[1]*(1 - Y1[1])*XX[i][0]
        W1[1,1] = W1[1,1] - a*E1[1]*Y1[1]*(1 - Y1[1])*XX[i][1]
        theta1[1] = theta1[1] - a*E1[1]*Y1[1]*(1 - Y1[1])
        #print("第1隐层的连接系数", W1)
        #print("第1隐层的阈值系数", theta1)
    print("平均总误差" + str(E/4.0))

下面用深度学习框架Tensorflow来模拟异或运算

训练过程如下

当采用(2,2,2)全连接层神经网络时,训练2000轮时,误差约为0.19,四个标签对应的输出为:

[0.43767142,0.56202793]→[0.,1.],

[0.5493321,0.45261452]→[1.,0.],

[0.575727,0.42299467]→[1.,0.],

[0.43716326,0.5625658 ]→[ 0.,1.]。

如果增加隐层的数量,将有效提高模拟效果,将隐层节点数量增加到4个,误差降到约0.16。

部分代码如下

import tensorflow as tf
import numpy as np
# 样本实例
XX = np.array([[0.0,0.0],
              [0.0,1.0],
              [1.0,0.0],
              [1.0,1.0]])
# 样本标签
L = np.array([[0.0,1.0],
              [1.0,0.0],
              [1.0,0.0],
              [0.0,1.0]])
tf_model = tf.keras.Sequential([
    tf.keras.layers.Dense(2, activation='sigmoid', input_shape=(2,), kernel_initializer='random_uniform', bias_initializer='zeros'),
    tf.keras.layers.Dense(2, activation='sigmoid', kernel_initializer='random_uniform', bias_initializer='zeros')
])
tf_model.compile(optimiaer=tf.keras.optimizers.SGD(), loss=tf.keras.losses.mean_squared_error, metrics=['accuracy'])
tf_model.summary()
tf_model.fit(XX, L, batch_size=4, epochs=2000, verbose=1)
tf_model.evaluate(XX, L)

创作不易 觉得有帮助请点赞关注收藏~~~

相关文章
|
17天前
|
机器学习/深度学习 算法 Java
机器学习、基础算法、python常见面试题必知必答系列大全:(面试问题持续更新)
机器学习、基础算法、python常见面试题必知必答系列大全:(面试问题持续更新)
|
27天前
|
机器学习/深度学习 算法 5G
基于BP神经网络的CoSaMP信道估计算法matlab性能仿真,对比LS,OMP,MOMP,CoSaMP
本文介绍了基于Matlab 2022a的几种信道估计算法仿真,包括LS、OMP、NOMP、CoSaMP及改进的BP神经网络CoSaMP算法。各算法针对毫米波MIMO信道进行了性能评估,通过对比不同信噪比下的均方误差(MSE),展示了各自的优势与局限性。其中,BP神经网络改进的CoSaMP算法在低信噪比条件下表现尤为突出,能够有效提高信道估计精度。
35 2
|
30天前
|
机器学习/深度学习 算法 Python
探索机器学习中的决策树算法:从理论到实践
【10月更文挑战第5天】本文旨在通过浅显易懂的语言,带领读者了解并实现一个基础的决策树模型。我们将从决策树的基本概念出发,逐步深入其构建过程,包括特征选择、树的生成与剪枝等关键技术点,并以一个简单的例子演示如何用Python代码实现一个决策树分类器。文章不仅注重理论阐述,更侧重于实际操作,以期帮助初学者快速入门并在真实数据上应用这一算法。
|
6天前
|
机器学习/深度学习 人工智能 算法
探索机器学习中的决策树算法
【10月更文挑战第29天】本文将深入浅出地介绍决策树算法,一种在机器学习中广泛使用的分类和回归方法。我们将从基础概念出发,逐步深入到算法的实际应用,最后通过一个代码示例来直观展示如何利用决策树解决实际问题。无论你是机器学习的初学者还是希望深化理解的开发者,这篇文章都将为你提供有价值的见解和指导。
|
26天前
|
机器学习/深度学习 算法 数据处理
EM算法对人脸数据降维(机器学习作业06)
本文介绍了使用EM算法对人脸数据进行降维的机器学习作业。首先通过加载ORL人脸数据库,然后分别应用SVD_PCA、MLE_PCA及EM_PCA三种方法实现数据降维,并输出降维后的数据形状。此作业展示了不同PCA变种在人脸数据处理中的应用效果。
29 0
|
10天前
|
设计模式 开发者 Python
Python编程中的设计模式:工厂方法模式###
本文深入浅出地探讨了Python编程中的一种重要设计模式——工厂方法模式。通过具体案例和代码示例,我们将了解工厂方法模式的定义、应用场景、实现步骤以及其优势与潜在缺点。无论你是Python新手还是有经验的开发者,都能从本文中获得关于如何在实际项目中有效应用工厂方法模式的启发。 ###
|
3天前
|
存储 人工智能 数据挖掘
从零起步,揭秘Python编程如何带你从新手村迈向高手殿堂
【10月更文挑战第32天】Python,诞生于1991年的高级编程语言,以其简洁明了的语法成为众多程序员的入门首选。从基础的变量类型、控制流到列表、字典等数据结构,再到函数定义与调用及面向对象编程,Python提供了丰富的功能和强大的库支持,适用于Web开发、数据分析、人工智能等多个领域。学习Python不仅是掌握一门语言,更是加入一个充满活力的技术社区,开启探索未知世界的旅程。
12 5
|
3天前
|
人工智能 数据挖掘 开发者
探索Python编程:从基础到进阶
【10月更文挑战第32天】本文旨在通过浅显易懂的语言,带领读者从零开始学习Python编程。我们将一起探索Python的基础语法,了解如何编写简单的程序,并逐步深入到更复杂的编程概念。文章将通过实际的代码示例,帮助读者加深理解,并在结尾处提供练习题以巩固所学知识。无论你是编程新手还是希望提升编程技能的开发者,这篇文章都将为你的学习之旅提供宝贵的指导和启发。
|
8天前
|
数据处理 Python
从零到英雄:Python编程的奇幻旅程###
想象你正站在数字世界的门槛上,手中握着一把名为“Python”的魔法钥匙。别小看这把钥匙,它能开启无限可能的大门,引领你穿梭于现实与虚拟之间,创造属于自己的奇迹。本文将带你踏上一场从零基础到编程英雄的奇妙之旅,通过生动有趣的比喻和实际案例,让你领略Python编程的魅力,激发内心深处对技术的渴望与热爱。 ###
|
11天前
|
数据采集 机器学习/深度学习 人工智能
Python编程入门:从基础到实战
【10月更文挑战第24天】本文将带你进入Python的世界,从最基础的语法开始,逐步深入到实际的项目应用。我们将一起探索Python的强大功能和灵活性,无论你是编程新手还是有经验的开发者,都能在这篇文章中找到有价值的内容。让我们一起开启Python的奇妙之旅吧!