现在正式开始,准备数据存放池,先看图:
按该图定义:
struct Vgg19模型
{
//组
层数据 * Conv1;//2
层数据 * Conv2;//2
层数据 * Conv3;//4
层数据 * Conv4;//4
层数据 * Conv5;//4
层数据 * fc6;//1
层数据 * fc7;//1
层数据 * fc8;//1 (共19层)
//构造函数
Vgg19模型();
};
建立:
Vgg19模型::Vgg19模型()
{
int size;
层数据 * 层;
//用于一层(宏)
/*输入维度,输出维度,核宽*/
#define 初始化ONE层(IN,OUT,KW) \
\
层->输入维度=IN;\
层->输出维度=OUT;\
层->核宽=KW;\
层->权重长度=层->输出维度*层->输入维度*层->核宽*层->核宽;\
层->权重_数据=(float*)malloc(sizeof(float) * 层->权重长度);\
层->偏移长度=层->输出维度;\
层->偏移_数据=(float*)malloc(sizeof(float) * 层->偏移长度);\
\
层++;\
//用于一组(宏)
/*组名称,输入维度,输出维度,核宽,组中层数*/
#define 初始化层(ConvX,IN,OUT,KW,Num) \
size = sizeof(层数据)*Num;\
\
层=ConvX =(层数据 *)malloc(size);\
初始化ONE层(IN,OUT,KW)\
for (int i=0;i<Num-1 ;i++ )\
{\
初始化ONE层(OUT,OUT,KW)\
}\
//Conv1: 2层
/*名称,输入维度,输出维度,核宽,组中层数*/
初始化层(Conv1,3,64,3,2)
//Conv2: 2层
初始化层(Conv2,64,128,3,2)
//Conv3: 4层
初始化层(Conv3,128,256,3,4)
//Conv4: 4层
初始化层(Conv4,256,512,3,4)
//Conv5: 4层
初始化层(Conv5,512,512,3,4)
//fc6: 1层
初始化层(fc6,512,4096,7,1)
//fc7: 1层
初始化层(fc7,4096,4096,1,1)
//fc8: 1层
初始化层(fc8,4096,1000,1,1)
}
现在可以载入数据了,把caffe的模型转换成文本方式(方法见之前的文章),500M的文件已经变成了3.4G了
下面载入:
bool loadModel(Vgg19模型 *sr)
{
char name[]= "VGG_ILSVRC_19_layers.caffemodel.txt";
std::ifstream fin(name);
//检查文件是否存在
if (!fin)
{
return false;
}
cout<<"正在载入‘Vgg19模型’的数据"<<endl;
//从档案载入
int len;
float * data;
层数据 * 层;
//读入卷积
//定义一个宏
#define 读入卷积(ConvX,Num) \
层=sr->ConvX;\
for (int i=0;i<Num ;i++ )\
{\
/*1。读入权重*/\
len=层->权重长度;/*需要载入的个数*/ \
data=层->权重_数据;\
\
in2(fin,len,data);\
\
/*2。读入偏移*/\
len=层->偏移长度;\
data=层->偏移_数据;\
\
in2(fin,len,data);\
层++;\
}\
cout<<"Conv1..."<<endl;
读入卷积(Conv1,2)
cout<<"Conv2..."<<endl;
读入卷积(Conv2,2)
cout<<"Conv3..."<<endl;
读入卷积(Conv3,4)
cout<<"Conv4..."<<endl;
读入卷积(Conv4,4)
cout<<"Conv5..."<<endl;
读入卷积(Conv5,4)
cout<<"fc6..."<<endl;
读入卷积(fc6,1)
cout<<"fc7..."<<endl;
读入卷积(fc7,1)
cout<<"fc8..."<<endl;
读入卷积(fc8,1)
cout<<"加载完成"<<endl;
fin.close ();
return true;
}
这个真的太慢了,应该是文件太大了,换一个c方式试试:
void in_c(FILE *fp,int &len, float * data);
bool loadModel2(Vgg19模型 *sr)
{
char name[]= "VGG_ILSVRC_19_layers.caffemodel.txt";//
cout<<"正在载入‘Vgg19模型’的数据"<<endl;
FILE *fp;
//if((fp=fopen(name,"r"))==NULL)
//if(fopen_s(&fp,name,"r")!=0)
if((fp=openfile(name,"r"))==NULL)
cout<<"打开文件出错了:"<<name<<endl;
//从档案载入
int len;
float * data;
层数据 * 层;
//读入卷积
//定义一个宏
#define 读入卷积2(ConvX,Num) \
层=sr->ConvX;\
for (int i=0;i<Num ;i++ )\
{\
/*1。读入权重*/\
len=层->权重长度;/*需要载入的个数*/ \
data=层->权重_数据;\
\
in_c(fp,len,data);\
\
/*2。读入偏移*/\
len=层->偏移长度;\
data=层->偏移_数据;\
\
in_c(fp,len,data);\
层++;\
}\
cout<<"Conv1..."<<endl;
读入卷积2(Conv1,2)
cout<<"Conv2..."<<endl;
读入卷积2(Conv2,2)
cout<<"Conv3..."<<endl;
读入卷积2(Conv3,4)
cout<<"Conv4..."<<endl;
读入卷积2(Conv4,4)
cout<<"Conv5..."<<endl;
读入卷积2(Conv5,4)
cout<<"fc6..."<<endl;
读入卷积2(fc6,1)
cout<<"fc7..."<<endl;
读入卷积2(fc7,1)
cout<<"fc8..."<<endl;
读入卷积2(fc8,1)
cout<<"加载完成"<<endl;
fclose(fp);
return true;
}
这个快一点了,但还是太慢,
如果把这个文件以二进制方式保存,再来读取是不是可以呢?
先这样吧