实验1 BP神经网络实验

传送门(所有的实验都使用python实现)

实验1 BP神经网络实验

实验2 som网实验

实验3 hopfield实现八皇后问题

实验4 模糊搜索算法预测薄冰厚度

实验5 遗传算法求解tsp问题

实验6 蚁群算法求解tsp问题

实验7 粒子群优化算法求解tsp问题

实验8 分布估计算法求解背包问题

实验9 模拟退火算法求解背包问题

实验10 禁忌搜索算法求解tsp问题

  • 实验目的
  1. 编程实现BP神经网络算法;
  2. 探究BP算法中学习因子算法收敛趋势、收敛速度之间的关系;
  3. 修改训练后BP神经网络部分连接权值,分析连接权值修改前和修改后对相同测试样本测试结果,理解神经网络分布存储等特点。
  • 实验要求

   按照下面的要求操作,然后分析不同操作后网络输出结果。

  1. 可修改学习因子
  2. 可任意指定隐单元层数
  3. 可任意指定输入层、隐含层、输出层的单元数
  4. 可指定最大允许误差ε
  5. 可输入学习样本(增加样本)
  6. 可存储训练后的网络各神经元之间的连接权值矩阵;
  7. 修改训练后的BP神经网络部分连接权值,分析连接权值修改前和修改后对相同测试样本测试结果 。
  • 实验原理
  1. 明确BP神经网络算法的基本思想如下:
  2. 明确BP神经网络算法步骤和流程如下:

四、实验内容和分析

  1. 实验时建立三层BP神经网络,输入节点2个,隐含层节点2个,输出节点1个,输入训练样本如下表:

表1 输入训练样本

输入值

输出

0.0

0.0

0.0

0.0

1.0

1.0

1.0

0.0

1.0

1.0

1.0

0.0

0.1

1.0

1.0

学习因子分别为0.9, 最大允许误差0.001。

  1. 训练结果:

  1. 输入测试样本为

0.05  0.1 

0.2   0.9 

0.86  0.95 

输出测试结果为

    

成功通过了测试,说明训练过程正确

1.改变学习因子

设置学习因子为0.6,学习因子越小结果越准确,但是也更耗时

2.改变输入层、隐含层、输出层的单元数

当隐含层节点个数为3时,相同训练样本和测试样本,得到测试结果为

隐含层变多之后,网络变复杂了,训练次数增多,但是结果更加准确。

最大允许误差ε控制网络识别精度。

精度取的越小,最后结果更精确,代价是付出更多的时间进行迭代。

以上实验误差均为0.001,本次取误差为0.0001,发现迭代次数上升,但是精度提高。

  1. 增加学习样本

在基本实验的基础上,增加一个学习样本0.1 1.0 1.0后

增加一个样本以后,虽然速度变慢,但是结果精度大大提高。

2.改变部分连接权值

为了保证算法能迅速收敛,因此采用的是随机梯度下降法,而非梯度下降法,因此算法是无监督型的,故不推荐修改连接权值。

1.实验过程:

由于BP算法的初始权重和阈值的随机性(为了保证梯度下降法的随机性,这里不使用固定的权重和阈值,可以使实验效果更好),因此实验的收敛次数是分散的,我们采用多次实验,取最小收敛次数作为依据。如图1所示。

1 部分实验过程

 实验过程如图1所示,多次执行算法,通过观察其收敛次数和测试结果的效果来决定是否采集本次数据。

2.实验结果:

本实验中,样本数据如表一所示,默认配置:最大迭代次数为10000,最大误差为0.001,学习因子为0.5,动量为0.9。实验结果在实验内容部分给出。

经过大量实验表明:

(1)一般来说,当算法迭代次数越多时,实验结果越精确,然而也存在特例,即算法陷入局部最小,迭代次数的增加并不带来精确度的提高。

python源码

# -*- coding: UTF-8 -*-
import random
import math
class bp:
    def init_w(self,w,x,y):#初始化偏置值
        for i in range(x):
            for j in range(y):
                w[i][j]=random.random()
                if(w[i][j]<0.5):w[i][j]=-w[i][j];
    def init_se(self,w,x):#初始化权值
        for i in range(x):
            w[i]=random.random()
            if(w[i]<0.5):
                w[i]=-w[i]
        
    def  forward(self,   inp,  outp,w, x, y, se):#向前传播输入
        for j in range(y):
            outp[j]=0
            for i in range(x):
                outp[j]+=inp[i]*w[i][j]
            outp[j] = outp[j]+se[j];
            outp[j] = (1.0)/(1+math.exp(-outp[j]))
    def  reforward(self):#反向误差更新
        self.sumse = 0;
        #计算输出层误差
        for i in range(self.o_size):
            self.eo[i] = self.ouput[i] * (1.0-self.ouput[i]) * (self.ouputex[i]-self.ouput[i]);
            if(self.eo[i]<0.0):
                self.sumse -= self.eo[i];
            else:
                self.sumse += self.eo[i]
        #计算输入层误差  
        for i in range(self.h_size):
            self. eh[i] = 0;
            for j in range(self.o_size):
                self. eh[i]+= self.hidden[i] * (1-self.hidden[i]) * self.who[i][j] * self.eo[j];
    def  updatew(self):
        #更新隐含层与输出层权值
        for i in range(self.h_size):
            for j in range(self.o_size):
                self.upwho[i][j]=(self.L*self.hidden[i]*self.eo[j])+(self.Mom*self.upwho[i][j])
                self.who[i][j]+=self.upwho[i][j]
        #更新输入与隐含层权值
        for i in range(self.i_size):
            for j in range(self.h_size):
                self.upwih[i][j]=(self.L*self.input[i]*self.eh[j])+(self.Mom*self.upwih[i][j])
                self.wih[i][j]+=self.upwih[i][j]   
        #更新阈值
    def  updatefa(self):
        for i in range(self.i_size):
            self.seh[i]+=self.L*self.eh[i]
        for i in range(self.o_size):
            self.seo[i]+=self.L*self.eo[i]
        #训练函数
    def  train(self ,in1,out1):
        self.input=in1
        self.ouputex=out1
        self.forward(self.input, self.hidden, self.wih, self.i_size, self.h_size, self.seh)#向前传播输入
        self.forward(self.hidden, self.ouput, self.who, self.h_size, self.o_size, self.seo)
        self.reforward()#反向误差传播
        self.updatew()#更新网络权重
        self.updatefa()#更新阈值
    #测试函数
    def test(self,init1):
        self.input=init1
        self.forward(self.input, self.hidden, self.wih, self.i_size, self.h_size, self.seh)
        self.forward(self.hidden, self.ouput, self.who, self.h_size, self.o_size, self.seo)
        for i in range(self.o_size):
            print(self.ouput[i])
    #返回阈值
    def get_e(self,w,x):
        self.f=0
        for i in range(self.o_size):
            print(w[i],end="")
            self.f+=1
            if(self.f%2==0):
                print("")    
        print("")
    #返回权值          
    def get_w(self,w,x,y):
        self.f=0;
        for i in range(x):
            for j in range(y):
                print(w[i][j],end="")
                print("     ",end="")
                self.f+=1
                if(self.f%2==0):
                    print("")         
    #类初始化                  
    def __init__(self,size,l,mom):

        self.L=l                        #学习因子                                                                                    
        self.Mom=mom;        #动量
        self.i_size=size[0];          #输入层数量
        self.h_size=size[1];        #隐含层数量
        self.o_size=size[2];          #输出层数量
        self.wih=[[0 for i in range(self.h_size)] for j in range(self.i_size)]    #输入层与隐含层权值
        self.who=[[0 for i in range(self.o_size)] for j in range(self.h_size)]     #隐含层与输出层权值
        self.upwih=[[0 for i in range(self.h_size)] for j in range(self.i_size)]    
        self.upwho=[[0 for i in range(self.o_size)] for j in range(self.h_size)]     # 动量更新
        self.input=[0 for i in range(self.i_size)]                      #输入层  
        self.hidden=[0 for i in range(self.h_size)]                #隐含层
        self.ouput=[0 for i in range(self.o_size)]                   #输出层
        self.ouputex=[0 for i in range(self.o_size)]                #期待输出
        self.seh= [0 for i in range(self.h_size)]                       #隐含层偏置
        self.seo= [0 for i in range(self.o_size)]                       #输出层偏置
        self.eh= [0 for i in range(self.h_size)]                       #隐含层误差
        self.eo= [0 for i in range(self.o_size)]                       #输出层误差
        
        self. init_w(self.wih,self.i_size,self.h_size)          #初始化 输入层到隐含层
        self. init_w(self.who,self.h_size,self.o_size)         #初始化 隐含层到输出层.
         
        self.init_se(self.seh, self.h_size)#初始化隐含层的偏置
        self.init_se(self.seo, self.o_size)#初始化输出层的偏置
    
           
         
size =[2,2,1]
inputData = [[0.0,0.0],[0.0,1.0],[1.0,0.0],[1.0,1.0],[0.1,1.0],[0.1,1.0]]
outputData = [[0.0],[1.0],[1.0],[0.0],[1.0],[1.0]]
testData = [[0.05,0.1],[0.2,0.9],[0.86,0.95]]


t=bp(size,0.5,0.9)

for i in range(10000):
    for j in range(6):
        t.train(inputData[j],outputData[j])
    if(t.sumse<0.001): 
        print("迭代次数:",i)
        break
    
print("误差为:",t.sumse)  
print("输入层与隐含层连接权值为:",end="")
t.get_w(t.wih,t.i_size,t.h_size)
print("隐含层与输出层连接权值为:",end="")
t.get_w(t.who,t.h_size,t.o_size)
print("隐含层神经元阈值为:",end="")
t.get_e(t.seh, t.h_size)
print("输出层神经元阈值为:",end="")
t.get_e(t.seo, t.o_size)
    
for i in range(3):
    print("训练样本为:",testData[i],"        结果为:",end="")
    t.test(testData[i])

         
  • 10
    点赞
  • 112
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 5
    评论
BP神经网络是一种常用的人工神经网络模型,常用于分类、回归、预测等任务。在Python中,我们可以使用第三方库如TensorFlow、Keras、PyTorch等来实现BP神经网络模型。 下面是一个简单的BP神经网络实验,使用Python和Keras库实现手写数字识别: 1. 数据准备 我们使用MNIST数据集,该数据集包括60000张训练图像和10000张测试图像,每张图片的大小为28x28,共有10个类别(0-9)。 我们可以使用Keras库中的mnist.load_data()函数来加载MNIST数据集: ```python from keras.datasets import mnist # 加载MNIST数据集 (train_images, train_labels), (test_images, test_labels) = mnist.load_data() ``` 2. 数据预处理 由于BP神经网络模型的输入必须是一维向量,因此我们需要将28x28的图像数据展开成一维向量。同时,我们还需要将图像数据标准化,将像素值缩放到0-1之间。 ```python # 数据预处理 train_images = train_images.reshape((60000, 28 * 28)) train_images = train_images.astype('float32') / 255 test_images = test_images.reshape((10000, 28 * 28)) test_images = test_images.astype('float32') / 255 ``` 3. 构建模型 我们使用Keras库来构建BP神经网络模型。下面是一个简单的模型,包括3个全连接层: ```python from keras import models from keras import layers # 构建BP神经网络模型 network = models.Sequential() network.add(layers.Dense(512, activation='relu', input_shape=(28 * 28,))) network.add(layers.Dense(10, activation='softmax')) ``` 4. 编译模型 在训练模型之前,我们需要编译模型。我们需要为模型选择损失函数、优化器和评估指标。 ```python # 编译模型 network.compile(optimizer='rmsprop', loss='categorical_crossentropy', metrics=['accuracy']) ``` 5. 训练模型 我们使用训练数据来训练模型,并使用测试数据来评估模型的性能。 ```python # 训练模型 network.fit(train_images, train_labels, epochs=5, batch_size=128) # 评估模型 test_loss, test_acc = network.evaluate(test_images, test_labels) print('test_acc:', test_acc) ``` 6. 预测结果 训练好的模型可以用来预测新的图像数据。下面是一个预测的例子: ```python # 预测结果 predictions = network.predict(test_images) # 显示预测结果 import numpy as np np.argmax(predictions[0]) # 预测结果 test_labels[0] # 真实结果 ``` 以上就是一个简单的BP神经网络实验,使用Python和Keras库实现手写数字识别。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Blaze Jack

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值