“程序设计与算法训练”课程设计:“BP神经网络的实现”(C++类封装实现)
一 题目:
71 BP神经网络的实现:
利用C++语言实现BP神经网络, 并利用BP神经网络解决螨虫分类问题:
蠓虫分类问题:对两种蠓虫(A与B)进行鉴别,依据的资料是触角和翅膀的长度,已知了9支Af和6支Apf 的数据如下:A: (1.24,1.27), (1.36,1.74),(1.38,1.64) , (1.38,1.82) , (1.38,1.90) , (1.40,1.70) , (1.48,1.82) , (1.54,1.82) ,(1.56,2.08).B: (1.14,1.82), (1.18,1.96), (1.20,1.86), (1.26,2.00), (1.28,2.00),(1.30,1.96).
要求:(1)阐述BP神经网络的结构构成及数学原理;
(2)利用C++实现BP神经网络;
(3)利用BP神经网络实现螨虫分类.
二 源代码:
头文件necessary.h:
#include<iostream>
#include<fstream>
#include<iomanip>
#include<stdlib.h>
#include<math.h>
#include<time.h> #define SampleCount 15 //学习样本个数
#define INnum 2 //输入层神经元数目
#define HN 15//隐层神经元数目
#define ONnum 1 //输出层神经元数目 using namespace std;
头文件bp.h:
#ifndef BP_H
#define BP_H #include "necessary.h" class Back_propagation
{ public:
Back_propagation();
double W[HN][INnum]; //输入层至隐层权值
double V[ONnum][HN]; //隐层至输出层权值
double P[INnum]; //单个样本输入数据
double T[ONnum]; //单个样本期望输出值 double OLD_W[HN][INnum]; //保存HN-IN旧权!
double OLD_V[ONnum][HN]; //保存ON-HN旧权!
double HI[HN]; //隐层的输入
double OI[ONnum]; //输出层的输入
double hidenLayerOutput[HN]; //隐层的输出
double OO[ONnum]; //输出层的输出
double err_m[SampleCount]; //第m个样本的总误差
double studyRate;//学习效率效率
double b;//步长
double e_err[HN];
double d_err[ONnum];
void input_p(int m);
void input_t(int m);
void H_I_O();
void O_I_O();
void Err_Output_Hidden(int m);
void Err_Hidden_Input();
void Adjust_O_H(int m,int n);
void Adjust_H_I(int m,int n);
void saveWV();
struct
{
double input[INnum];
double teach[ONnum];
}Study_Data[SampleCount];
private:
}; #endif
源文件necessary.cpp:
#include "necessary.h"
源文件bp.cpp:
#include"bp.h" Back_propagation::Back_propagation()
{ srand( (unsigned)time( NULL ) ); for( int i = ; i < HN; i ++ )
{
for( int j = ; j < INnum; j ++ )
{
W[i][j] = double( rand() % ) / ; //初始化输入层到隐层的权值
}
}
for( int ii = ; ii < ONnum; ii ++ )
{
for( int jj = ; jj < HN; jj ++ )
{
V[ii][jj] = double( rand() % ) / ; //初始化隐层到输出层的权值
}
}
} void Back_propagation::input_p(int m)
{
for( int i = ; i < INnum; i ++ )
{
P[i] = Study_Data[m].input[i];
}
} void Back_propagation::input_t(int m)
{
for( int k = ; k < ONnum; k ++ )
{
T[k] = Study_Data[m].teach[k];
}
} void Back_propagation::H_I_O()
{
double net;
int i,j;
for( j = ; j < HN; j ++ )
{
net = ;
for( i = ; i < INnum; i ++ )
{
net += W[j][i] * P[i];//求隐层内积
}
HI[j] = net;// - Thread_Hiden[j];//求隐层输入
hidenLayerOutput[j] = 1.0 / ( 1.0 + exp(-HI[j]) );//求隐层输出
}
} void Back_propagation::O_I_O()
{
double net;
int k,j;
for( k = ; k < ONnum; k ++ )
{
net = ;
for( j = ; j < HN; j ++ )
{
net += V[k][j] * hidenLayerOutput[j];//求输出层内积
}
OI[k] = net; //求输出层输入
OO[k] = 1.0 / ( 1.0 + exp(-OI[k]) );//求输出层输出
}
} void Back_propagation::Err_Output_Hidden( int m )
{
double abs_err[ONnum];//样本误差
double sqr_err = ;//临时保存误差平方 for( int k = ; k < ONnum; k ++ )
{
abs_err[k] = T[k] - OO[k]; //求第m个样本下的第k个神经元的绝对误差 sqr_err += (abs_err[k]) * (abs_err[k]);//求第m个样本下输出层的平方误差 d_err[k] = abs_err[k] * OO[k] * (1.0-OO[k]);//d_err[k]输出层各神经元的一般化误差
}
err_m[m] = sqr_err / ;//第m个样本下输出层的平方误差/2=第m个样本的均方误差,据ppt1.5-3 } void Back_propagation::Err_Hidden_Input()
{
double sigma;
for( int j = ; j < HN; j ++ )
{
sigma = 0.0;
for( int k = ; k < ONnum; k ++ )
{
sigma += d_err[k] * V[k][j];
} e_err[j] = sigma * hidenLayerOutput[j] * ( - hidenLayerOutput[j] );//隐层各神经元的一般化误差
}
} void Back_propagation::Adjust_O_H( int m,int n )
{
if( n <= )
{
for( int k = ; k < ONnum; k ++ )
{
for( int j = ; j < HN; j ++ )
{
V[k][j] = V[k][j] + studyRate * d_err[k] * hidenLayerOutput[j];//输出层至隐层的权值调整
}
}
}
else if( n > )
{
for( int k = ; k < ONnum; k ++ )
{
for( int j = ; j < HN; j ++ )
{
V[k][j] = V[k][j] + studyRate * d_err[k] * hidenLayerOutput[j] + b * ( V[k][j] - OLD_V[k][j] );//输出层至隐层的权值调整
}
}
}
} void Back_propagation::Adjust_H_I( int m,int n )
{
if( n <= )
{
for( int j = ; j < HN; j ++ )
{
for ( int i = ; i < INnum; i ++ )
{
W[j][i] = W[j][i] + studyRate * e_err[j] * P[i];//隐层至输入层的权值调整
}
} }
else if( n > )
{
for( int j = ; j < HN; j ++ )
{
for( int i = ; i < INnum; i ++ )
{
W[j][i] += studyRate * e_err[j] * P[i] + b * ( W[j][i] - OLD_W[j][i] );//隐层至输入层的权值调整
}
}
}
} void Back_propagation::saveWV()
{
for( int i = ; i < HN; i ++ )
{
for( int j = ; j < INnum; j ++ )
{
OLD_W[i][j] = W[i][j];
}
} for( int ii = ; ii < ONnum; ii ++ )
{
for( int jj = ; jj < HN; jj ++ )
{
OLD_V[ii][jj] = V[ii][jj];
}
}
}
源文件main.cpp:
#include "bp.h" void saveWV( Back_propagation bp )
{
for( int i = ; i < HN; i ++ )
{
for( int j = ; j < INnum; j ++ )
{
bp.OLD_W[i][j] = bp.W[i][j];
}
} for( int ii = ; ii < ONnum; ii ++ )
{
for( int jj = ; jj < HN; jj ++ )
{
bp.OLD_V[ii][jj] = bp.V[ii][jj];
}
}
} //保存数据
void savequan( Back_propagation bp )
{
ofstream outW( "w.txt" );
ofstream outV( "v.txt" ); for( int i = ; i < HN; i ++ )
{
for( int j = ; j < INnum; j ++ )
{
outW << bp.W[i][j] << " ";
}
outW << "\n";
} for( int ii = ; ii < ONnum; ii ++ )
{
for( int jj = ; jj < HN; jj ++ )
{
outV << bp.V[ii][jj] << " ";
}
outV << "\n";
} outW.close();
outV.close(); } double Err_Sum( Back_propagation bp )
{
double total_err = ;
for ( int m = ; m < SampleCount; m ++ )
{
total_err += bp.err_m[m];//每个样本的均方误差加起来就成了全局误差
}
return total_err;
} int main()
{
double sum_err;
int study;
int m;
double check_in, check_out;
ifstream Train_in( "trainin.txt", ios::in );
ifstream Train_out( "trainout.txt", ios::in ); if( ( Train_in.fail() ) || ( Train_out.fail() ) )
{
//printf( "Error input file!\n" );
cerr << "Error input file!" << endl;
exit();
} Back_propagation bp; cout << "请输入学习效率: studyRate = ";
cin >> bp.studyRate; cout << "\n请输入步长: b= ";
cin >> bp.b; study = ;
double Pre_error ; //预定误差
cout << "\n请输入预定误差: Pre_error = ";
cin >> Pre_error; int Pre_times;
cout << "\n请输入预定最大学习次数:Pre_times=";
cin >> Pre_times; for( m = ; m < SampleCount; m ++ )
{
for( int i = ; i < INnum; i ++ )
{
Train_in >> bp.Study_Data[m].input[i];
}
} cout << endl;
for( m = ; m < SampleCount; m ++ )
{
for( int k = ; k < ONnum; k ++ )
{
Train_out >> bp.Study_Data[m].teach[k];
}
} cout << endl; do
{
++ study;
if( study > Pre_times )
{
cout << "训练失败!" << endl;
break;
} for ( int m = ; m < SampleCount; m ++ )
{
bp.input_p(m); //输入第m个学习样本 (2)
bp.input_t(m);//输入第m个样本的教师信号 (3)
bp.H_I_O(); //第m个学习样本隐层各单元输入、输出值 (4)
bp.O_I_O();
bp.Err_Output_Hidden(m); //第m个学习样本输出层至隐层一般化误差 (6)
bp.Err_Hidden_Input(); //第m个学习样本隐层至输入层一般化误差 (7)
bp.Adjust_O_H(m,study);
bp.Adjust_H_I(m,study);
if( m == )
{
cout << bp.V[][] << " " << bp.V[][] << endl;
}
}//全部样本训练完毕
sum_err = Err_Sum(bp); //全部样本全局误差计算 (10)
bp.saveWV();
}while( sum_err > Pre_error ); if( ( study <= Pre_times ) & ( sum_err < Pre_error ) )
{
cout << "训练结束!" << endl;
cout << "你已经学习了 " << study << "次" << endl;
}
double net;
int k, j;
while()
{
printf( "请输入蠓虫的触角及翅膀的长度:" );
cin >> check_in;
cin >> check_out;
bp.P[] = check_in;
bp.P[] = check_out;
bp.H_I_O();
for ( k = ; k < ONnum; k ++ )
{
net = ;
for( j = ; j < HN; j ++ )
{
net += bp.V[k][j] * bp.hidenLayerOutput[j];//求输出层内积
}
bp.OI[k] = net; //求输出层输入
bp.OO[k] = 1.0 / ( 1.0 + exp(-bp.OI[k]) );//求输出层输出
}
if( bp.OO[] > 0.5 )
{
printf( "该蠓虫是af!\n" );
}
else if( bp.OO[] >= )
{
printf( "该蠓虫是apf!\n" );
}
}
return ;
}
三 测试文件:
文件trainin.txt:
1.24 1.27
1.36 1.74
1.38 1.64
1.38 1.82
1.38 1.90
1.40 1.70
1.48 1.82
1.54 1.82
1.56 2.08
1.14 1.82
1.18 1.96
1.20 1.86
1.26 2.00
1.28 2.00
1.30 1.96
文件trainout.txt:
四 实验结果:
图1 输入数据
图2 测试算法“学习”结果
附录:
题目里面既有“螨(音mǎn)虫”,也有“蠓(音měng)虫”,程序里面用的是“蠓虫”。
参考文献:
[1]甘刚.BP算法在IDS中应用与实现的研究[J].成都:电子科技大学,硕博学位论文,2005.
“程序设计与算法训练”课程设计:“BP神经网络的实现”(C++类封装实现)的更多相关文章
- 模式识别之ocr项目---(模板匹配&BP神经网络训练)
摘 要 在MATLAB环境下利用USB摄像头采集字符图像,读取一帧保存为图像,然后对读取保存的字符图像,灰度化,二值化,在此基础上做倾斜矫正,对矫正的图像进行滤波平滑处理,然后对字符区域进行提取分割出 ...
- 字符识别OCR研究一(模板匹配&BP神经网络训练)
摘 要 在MATLAB环境下利用USB摄像头採集字符图像.读取一帧保存为图像.然后对读取保存的字符图像,灰度化.二值化,在此基础上做倾斜矫正.对矫正的图像进行滤波平滑处理,然后对字符区域进行提取切割出 ...
- BP神经网络分类器的设计
1.BP神经网络训练过程论述 BP网络结构有3层:输入层.隐含层.输出层,如图1所示. 图1 三层BP网络结构 3层BP神经网络学习训练过程主要由4部分组成:输入模式顺传播(输入模式由输入层经隐含层向 ...
- 基于BP神经网络的简单字符识别算法自小结(C语言版)
本文均属自己阅读源代码的点滴总结.转账请注明出处谢谢. 欢迎和大家交流.qq:1037701636 email:gzzaigcn2009@163.com 写在前面的闲话: 自我感觉自己应该不是一个非常 ...
- BP神经网络算法预测销量高低
理论以前写过:https://www.cnblogs.com/fangxiaoqi/p/11306545.html,这里根据天气.是否周末.有无促销的情况,来预测销量情况. function [ ma ...
- R_Studio(神经网络)BP神经网络算法预测销量的高低
BP神经网络 百度百科:传送门 BP(back propagation)神经网络:一种按照误差逆向传播算法训练的多层前馈神经网络,是目前应用最广泛的神经网络 #设置文件工作区间 setwd('D:\\ ...
- bp神经网络算法
对于BP神经网络算法,由于之前一直没有应用到项目中,今日偶然之时 进行了学习, 这个算法的基本思路是这样的:不断地迭代优化网络权值,使得输入与输出之间的映射关系与所期望的映射关系一致,利用梯度下降的方 ...
- 神经网络中的BP神经网络和贝叶斯
1 贝叶斯网络在地学中的应用 1 1.1基本原理及发展过程 1 1.2 具体的研究与应用 4 2 BP神经网络在地学中的应用 6 2.1BP神经网络简介 6 2.2基本原理 7 2.3 在地学中的具体 ...
- BP神经网络与Python实现
人工神经网络是一种经典的机器学习模型,随着深度学习的发展神经网络模型日益完善. 联想大家熟悉的回归问题, 神经网络模型实际上是根据训练样本创造出一个多维输入多维输出的函数, 并使用该函数进行预测, 网 ...
随机推荐
- 洛谷1052(路径压缩后简单dp)
同POJ3744写法都是一样的. 距离太长无意义可以压缩,注意不是随便压的,想一想可以跟%T发生关系. #include <cstdio> #include <cctype> ...
- 【Codeforces1111D_CF1111D】Destroy the Colony(退背包_组合数学)
题目: Codeforces1111D 翻译: [已提交至洛谷CF1111D] 有一个恶棍的聚居地由几个排成一排的洞穴组成,每一个洞穴恰好住着一个恶棍. 每种聚居地的分配方案可以记作一个长为偶数的字符 ...
- Metasploits之ms10_018
漏洞详情:https://technet.microsoft.com/library/security/ms10-018 一准备: 1:kali Linux系统 192.168.195.129 2:W ...
- 计算机中如何实现除数是2的幂次的除法【转载自CSDN】
前言: 本来是在看汇编里面的数据条件传送指令,做习题的时候看着这么一道有关于2的幂次方除法的题目.结果傻眼了,又尼玛不会了.........第二章看的时候就稀里糊涂的,看了几遍也没看太懂,这回又涉及到 ...
- split()分割字符串用法
<script type="text/javascript"> var str="How are you doing today?" documen ...
- Linux 查找bom头文件,清除bom头命令
1.查找bom头文件 grep -r -I -l $'^\xEF\xBB\xBF' ./ 2.替换bom头文件 find . -type f -exec sed -i 's/\xEF\xBB\xBF/ ...
- DB2中横表纵表互换
1.列转行:创建一个如下的表drop table dwtmp.tmp_xn_lsb; create table dwtmp.tmp_xn_lsb ( year int ,quarter ...
- [转]SqlServer索引的原理与应用
索引的概念 索引的用途:我们对数据查询及处理速度已成为衡量应用系统成败的标准,而采用索引来加快数据处理速度通常是最普遍采用的优化方法. 索引是什么:数据库中的索引类似于一本书的目录,在一本书中使用目录 ...
- android 常用第三方github工程
这里有个汇总的网址:http://androidxy.com/zh/page/latest/-1/0 数据库:greenDao 参考:GreenDao3.2的使用 控件注解:Butterknife 图 ...
- 微软爆料新型系统,Windows7,Windows10强势来袭
本系统是10月5日最新完整版本的Windows10 安装版镜像,win10正式版,更新了重要补丁,提升应用加载速度,微软和百度今天宣布达成合作,百度成为win10 Edge浏览器中国默认主页和搜索引擎 ...