c++和cuda混合编程 实现传统神经网络
直接放代码了。。。
实现的是x1+x2=y的预测,但梯度下降很慢。。。233333,gpu运行时间很快!!
//
// main.cpp
// bp
//
// Created by jzc on 2018/4/18.
// Copyright © 2018年 jzc. All rights reserved.
//
#include <stdio.h>
#include <iostream>
#include <time.h>
#include <stdlib.h>
#include <math.h>
#include <fstream>
#include <cuda_runtime.h>
using namespace std;
#define DATASIZE 10000
#define TESTSIZE 100
#define NEURESIZE 50
#define RW 0.1
#define EPOCH 1000
#define E 2.71828
//打印设备信息
void printDeviceProp(const cudaDeviceProp &prop)
{
printf("Device Name : %s.\n", prop.name);
printf("totalGlobalMem : %ld.\n", prop.totalGlobalMem);
printf("sharedMemPerBlock : %ld.\n", prop.sharedMemPerBlock);
printf("regsPerBlock : %d.\n", prop.regsPerBlock);
printf("warpSize : %d.\n", prop.warpSize);
printf("memPitch : %ld.\n", prop.memPitch);
printf("maxThreadsPerBlock : %d.\n", prop.maxThreadsPerBlock);
printf("maxThreadsDim[0 - 2] : %d %d %d.\n", prop.maxThreadsDim[], prop.maxThreadsDim[], prop.maxThreadsDim[]);
printf("maxGridSize[0 - 2] : %d %d %d.\n", prop.maxGridSize[], prop.maxGridSize[], prop.maxGridSize[]);
printf("totalConstMem : %ld.\n", prop.totalConstMem);
printf("major.minor : %d.%d.\n", prop.major, prop.minor);
printf("clockRate : %d.\n", prop.clockRate);
printf("textureAlignment : %ld.\n", prop.textureAlignment);
printf("deviceOverlap : %d.\n", prop.deviceOverlap);
printf("multiProcessorCount : %d.\n", prop.multiProcessorCount);
} //CUDA 初始化
bool InitCUDA()
{
int count; //取得支持Cuda的装置的数目
cudaGetDeviceCount(&count); if (count == ) {
fprintf(stderr, "There is no device.\n");
return false;
} int i; for (i = ; i < count; i++) { cudaDeviceProp prop;
cudaGetDeviceProperties(&prop, i);
//打印设备信息
printDeviceProp(prop); if (cudaGetDeviceProperties(&prop, i) == cudaSuccess) {
if (prop.major >= ) {
break;
}
}
} if (i == count) {
fprintf(stderr, "There is no device supporting CUDA 1.x.\n");
return false;
} cudaSetDevice(i); return true;
}
void init(int num,int range,double a[],double offset){
for(int i=;i<num;i++){
a[i] = (double)(rand()%(range*)/1000.0) - offset;
}
} void getM(int num,double a[],double m[]){
m[] = m[] = 0.0;
for(int i=;i<num;i++){
if(a[i]<m[]){
m[] = a[i];
}else if(a[i]>m[]){
m[] = a[i];
}
}
} void normalize(int num,double a[],double m[]){
for(int i =;i<num;i++){
a[i] = (a[i]-m[]+)/(m[]-m[]+);
}
} void renorm(int num,double a[],double m[]){
for(int i =;i<num;i++){
a[i] = a[i]*(m[]-m[]+) + m[] - ;
}
} void printArray(int num,double a[]){
for(int i=;i<num;i++){
printf("%6.4lf ",a[i]);
if((i+)%==){
cout<<endl;
}
}
} __global__ static void hidenLayer(double x1,double x2,double w1[],double w2[],double yh[]){
/*for(int i=0;i<NEURESIZE;i++){
yh[i] = w1[i]*x1 + w2[i]*x2;
yh[i] = 1/(1+pow(E,0-yh[i]));
}*/
const int tid = threadIdx.x;
int i =tid;
yh[i] = w1[i]*x1 + w2[i]*x2;
yh[i] = /(+pow(E,-yh[i]));
} double outLayer(double yh[],double v[]){
double y2;
for(int i=;i<NEURESIZE;i++){
y2 += yh[i] * v[i];
}
y2 = /(+pow(E,-y2));
return y2; } __global__ static void update(double x1[],double x2[],double yh[],double v[],double w1[],double w2[],double *loss){
const int tid = threadIdx.x;
int i = tid;
/*for(int i=0;i<NEURESIZE;i++){
w1[i] += x1[i] * (1-x1[i]) * loss * RW;
w2[i] += x2[i] * (1-x2[i]) * loss * RW;
v[i] += yh[i] * loss * RW;
}*/
w1[i] += x1[i] * (-x1[i]) * (*loss) * RW;
w2[i] += x2[i] * (-x2[i]) * (*loss) * RW;
v[i] += yh[i] * (*loss) * RW;
} /*double test(double w1[],double w2[],double v[],double m1[],double m2[],double my[]){
double tx1[TESTSIZE],tx2[TESTSIZE],ty[TESTSIZE],tyh[NEURESIZE],ty2[TESTSIZE];
double avLoss = 0.0; init(TESTSIZE,10,tx1,0.0);
init(TESTSIZE,10,tx2,0.0); for(int i=0;i<TESTSIZE;i++){
ty[i] = tx1[i] + tx2[i];
}
normalize(TESTSIZE,tx1,m1);
normalize(TESTSIZE,tx2,m2);
for(int q=0;q<TESTSIZE;q++){
hidenLayer(tx1[q],tx2[q],w1,w2,tyh);
ty2[q] = outLayer(tyh,v);
} renorm(TESTSIZE,ty2,my);
for(int i=0;i<TESTSIZE;i++){
if(i<10){
printf("%2d y=%2.4f y2=%2.4f\n",i,ty[i],ty2[i]);
}
avLoss += pow(ty[i]-ty2[i],2);
}
avLoss /= TESTSIZE;
//cout<<avLoss<<endl;
return avLoss;
}*/ int main(){
ofstream outf;
outf.open("trainloss.txt");
srand( (unsigned)time(NULL) );
long starttime = clock();
double x1[DATASIZE],x2[DATASIZE],y[DATASIZE],y2[DATASIZE];
double w1[NEURESIZE],w2[NEURESIZE],v[NEURESIZE],yh[NEURESIZE];
double m1[],m2[],my[];
double cLoss,realLoss,minTrainLoss = 1.0,minTestLoss = 1.0;
init(DATASIZE,,x1,0.0);
init(DATASIZE,,x2,0.0);
init(NEURESIZE,,w1,1.0);
init(NEURESIZE,,w2,1.0);
init(NEURESIZE,,v,1.0); for(int i=;i<DATASIZE;i++){
y[i] = x1[i] + x2[i];
} //CUDA 初始化
if (!InitCUDA()) {
return ;
}
//cudaMalloc 取得一块显卡内存
double *x1_g,*x2_g,*y_g,*y2_g;
double *w1_g,*w2_g,*v_g,*yh_g;
double *cLoss_g;
cudaMalloc((void**)&x1_g, sizeof(double)* DATASIZE);
cudaMalloc((void**)&x2_g, sizeof(double)* DATASIZE);
cudaMalloc((void**)&y_g, sizeof(double)* DATASIZE);
cudaMalloc((void**)&y2_g, sizeof(double)* DATASIZE);
cudaMalloc((void**)&w1_g, sizeof(double)* NEURESIZE);
cudaMalloc((void**)&w2_g, sizeof(double)* NEURESIZE);
cudaMalloc((void**)&v_g, sizeof(double)* NEURESIZE);
cudaMalloc((void**)&yh_g, sizeof(double)* NEURESIZE);
cudaMalloc((void**)&cLoss_g, sizeof(double)); //cudaMemcpy 将产生的随机数复制到显卡内存中
//cudaMemcpyHostToDevice - 从内存复制到显卡内存
//cudaMemcpyDeviceToHost - 从显卡内存复制到内存
cudaMemcpy(w1_g,w1, sizeof(double)*NEURESIZE, cudaMemcpyHostToDevice);
cudaMemcpy(w2_g,w2, sizeof(double)*NEURESIZE, cudaMemcpyHostToDevice);
cudaMemcpy(v_g,v, sizeof(double)*NEURESIZE, cudaMemcpyHostToDevice);
cudaMemcpy(x1_g,x1, sizeof(double)*DATASIZE, cudaMemcpyHostToDevice);
cudaMemcpy(x2_g,x2, sizeof(double)*DATASIZE, cudaMemcpyHostToDevice);
cudaMemcpy(y_g,y, sizeof(double)*DATASIZE, cudaMemcpyHostToDevice);
cudaMemcpy(yh_g,yh, sizeof(double)*NEURESIZE, cudaMemcpyHostToDevice);
cudaMemcpy(cLoss_g,&cLoss, sizeof(double), cudaMemcpyHostToDevice); getM(DATASIZE,x1,m1);
getM(DATASIZE,x2,m2);
getM(DATASIZE,y,my);
normalize(DATASIZE,x1,m1);
normalize(DATASIZE,x2,m2);
normalize(DATASIZE,y,my); for(int j=;j<EPOCH;j++){
double tLoss = 0.0;
for(int i=;i<DATASIZE;i++){
hidenLayer<< < , NEURESIZE, >> >(x1_g[i],x2_g[i],w1_g,w2_g,yh_g);
cudaMemcpy(yh,yh_g, sizeof(double)*NEURESIZE, cudaMemcpyDeviceToHost);
cudaMemcpy(v,v_g, sizeof(double)*NEURESIZE, cudaMemcpyDeviceToHost);
y2[i] = outLayer(yh,v);
cLoss = y2[i] * (-y2[i]) * (y[i]-y2[i]);
cudaMemcpy(cLoss_g,&cLoss, sizeof(double), cudaMemcpyHostToDevice);
update<< < , NEURESIZE, >> >(x1_g,x2_g,yh_g,v_g,w1_g,w2_g,cLoss_g);
cudaMemcpy(&cLoss,cLoss_g, sizeof(double)*NEURESIZE, cudaMemcpyDeviceToHost);
cLoss = pow(cLoss,);
cLoss = cLoss*(my[]-my[]+);
tLoss += cLoss;
}
tLoss /= DATASIZE;
if(tLoss<minTrainLoss){
minTrainLoss = tLoss;
}
printf("EPOCH--%d, trainLoss--%0.4f\n",j,tLoss);
outf<<j<<"\t"<<tLoss<<endl; /*cudaMemcpy(w1,w1_g, sizeof(double)*NEURESIZE, cudaMemcpyDeviceToHost);
cudaMemcpy(w2,w2_g, sizeof(double)*NEURESIZE, cudaMemcpyDeviceToHost);
cudaMemcpy(v,v_g, sizeof(double)*NEURESIZE, cudaMemcpyDeviceToHost);
double avLoss = test(w1,w2,v,m1,m2,my);
printf("EPOCH--%d, avLoss--%0.4f\n",j,avLoss);
if(avLoss<minTestLoss){
minTestLoss = avLoss;
}*/
cout<<"------------------"<<endl;
}
printf("minTrainLoss--%0.4f\n",minTrainLoss);
//printf("minTestLoss--%0.4f\n",minTestLoss);
outf.close(); //Free
cudaFree(x1_g);
cudaFree(x2_g);
cudaFree(y_g);
cudaFree(w1_g);
cudaFree(w2_g);
cudaFree(v_g);
cudaFree(yh_g);
cudaFree(cLoss_g); long endtime = clock()-starttime;
float execution_time = (float)endtime / ( * );
cout << "total time cost: " << execution_time<<endl; return ;
}
c++和cuda混合编程 实现传统神经网络的更多相关文章
- mpi和cuda混合编程的正确编译
针对大数据的计算,很多程序通过搭建mpi集群进行加速,并取得了很好的效果.算法内部的加速,当前的并行化趋势是利用GPU显卡进行算法加速.针对并行性非常好的算法,GPU加速效果将远大于集群带来的加速效果 ...
- 【原创】Matlab.NET混合编程技巧之直接调用Matlab内置函数
本博客所有文章分类的总目录:[总目录]本博客博文总目录-实时更新 Matlab和C#混合编程文章目录 :[目录]Matlab和C#混合编程文章目录 在我的上一篇文章[ ...
- Matlab.NET混合编程技巧之——直接调用Matlab内置函数(附源码)
原文:[原创]Matlab.NET混合编程技巧之--直接调用Matlab内置函数(附源码) 在我的上一篇文章[原创]Matlab.NET混编技巧之——找出Matlab内置函数中,已经大概的介绍了mat ...
- CUDA+OpenGL混合编程
CUDA+OpenGL混合编程示例: #include <stdio.h> #include <stdlib.h> #include "GL\glew.h" ...
- [转载:]C#与Fortran混合编程之本地调用Fortran动态链接库
前言 C#发展到现在,已是一门相当完善的语言,他基于C语言风格,演化于C++.并依靠强大的.NET底层框架.C#可以用来快速构建桌面及Web应用.然而在我们的实际工作中,尽管C#已经非常完善,但还是不 ...
- Matlab与.NET基于类型安全的接口混合编程入门
原文:[原创]Matlab与.NET基于类型安全的接口混合编程入门 如果这些文章对你有用,有帮助,期待更多开源组件介绍,请不要吝啬手中的鼠标. [原创分享]Matlab.NET混编调用Figure窗体 ...
- Matlab与.NET混合编程解决人脸识别问题
原文:[原创]Matlab与.NET混合编程解决人脸识别问题 如果这些文章对你有用,有帮助,期待更多开源组件介绍,请不要吝啬手中的鼠标. [原创分享]Matlab.NET混编调用Figure窗体 ht ...
- 通过混合编程分析的方法和机器学习预测Web应用程序的漏洞
通过混合编程分析的方法和机器学习预测Web应用程序的漏洞 由于时间和资源的限制,web软件工程师需要支持识别出有漏洞的代码.一个实用的方法用来预测漏洞代码可以提高他们安全审计的工作效率.在这篇文章中, ...
- Android程序中,内嵌ELF可执行文件-- Android开发C语言混合编程总结
前言 都知道的,Android基于Linux系统,然后覆盖了一层由Java虚拟机为核心的壳系统.跟一般常见的Linux+Java系统不同的,是其中有对硬件驱动进行支持,以避开GPL开源协议限制的HAL ...
随机推荐
- golang --iota 用法
package main import "fmt" func main() { const ( a = iota //0 b //1 c //2 d = "ha" ...
- 全栈项目|小书架|服务器开发-Koa2 连接MySQL数据库(Navicat+XAMPP)
为什么使用数据库 为什么需要数据库?-知乎 相比与文件系统,数据库具有以下优势: 高效率:查找效率高 高可用:可数据库共享 安全性强:数据不能随意修改 选择哪个数据库 数据库可以分为关系型数据库和非关 ...
- JAVA基础之ServletContext应用
创建一个登陆的界面,并且统计次数! 导入jar包; 1. driver=com.mysql.jdbc.Driver url=jdbc:mysql://localhost:3306/java0603?u ...
- python 编码设置
py 文件设置编码: # -*- coding: utf-8 -*- #coding=utf-8 两种方式任选一种即可 输出到浏览器设置编码: import io import sys sys.std ...
- kubernetes-使用kubeadm部署kubernetes集群
k8s官网介绍 Kubernetes是一个可移植的,可扩展的开源平台,用于管理容器化的工作负载和服务,可促进声明式配置和自动化.它拥有一个庞大且快速增长的生态系统.Kubernetes的服务,支持和工 ...
- 交互式计算引擎MOLAP篇
交互式计算引擎MOLAP篇 摘自:<大数据技术体系详解:原理.架构与实践> MOLAP是一种通过预计算cube方式加速查询的OLAP引擎,它的核心思想是“空间换时间”,典型代表包括Drui ...
- Linux系统下文件压缩与打包命令
Linux系统下文件压缩与打包命令 常用的压缩文件拓展名 * .Z * .zip * .gz * .bz2 * .xz * .tar * .tar.gz * .tar.bz2 * .tar.xz 压缩 ...
- python算法与数据结构-插入排序算法(34)
一.插入排序的介绍 插入排序的工作方式非常像人们排序一手扑克牌一样.开始时,我们的左手为空并且桌子上的牌面朝下.然后,我们每次从桌子上拿走一张牌并将它插入左手中正确的位置.为了找到一张牌的正确位置,我 ...
- 0032ActiveMQ之java编码实现生产者和消费者操作队列queue
今天学习了入门级的用java编写生产者producer和消费者consumer操作activemq的queue队列,为了之后复习回顾,现做整理如下: maven工程的搭建此处不再讲解,在maven工程 ...
- 第三天Beta冲刺
团队作业Beta冲刺 项目 内容 这个作业属于哪个课程 任课教师博客主页链接 这个作业的要求在哪里 作业链接地址 团队名称 你们都是魔鬼吗 作业学习目标 (1)掌握软件黑盒测试技术:(2)学会编制软件 ...