首先列出了一些参照的文章,但是自己并没有完全按照这些配置,但是有重要参考价值。
重要参照link(优先级从上到下):
1. vs2013创建caffe工程
2. caffe-Windows 添加工程-以classification为例,这里面还有其他几个有用的链接。
已经配置好了caffe的基本环境,包括使用python的“import caffe”不出错,可按照https://blog.csdn.net/woha1yo/article/details/117473594配置 Debug和Release环境,并且libraries_v140_x64_py35_1.1.0.tar.bz2已经解压至对应目录“C:\Users\MWG.caffe\dependencies\libraries_v140_x64_py35_1.1.0\libraries”,后续会用到,下载地址为https://pan.baidu.com/s/1qYdrSE4#list/path=%2F。
使用VS2015新建空项目“cpp_classification”;拷贝文件cpp_classification.cpp(地址caffe-window/examples/cpp_classification目录下)至VS2015新建的目录下;右键源文件添加现有项,选中“classification.cpp”。
配置包含目录(include),库目录(lib)和附加依赖项(xxx.lib)
包含目录,VC++目录 -> 包含目录
添加caffe-window的包含目录
D:\caffe-windows\include
使用protoc.exe生成,并拷贝到对应目录下, 使用目录
C:\Users\MWG\.caffe\dependencies\libraries_v140_x64_py35_1.1.0\libraries\bin
下的 protoc.exe,将其拷贝至目录
D:\caffe-windows\src\caffe\proto
并新建makefile.bat文件,内容为
protoc.exe caffe.proto --cpp_out=.\
pause
保存之后,直接运行,该bat会将caffe.proto生成 caffe.pb.cc和caffe.pb.h。注意protoc.exe的版本不能太高,否则会出错,最好就是编译caffe时的版本最好,否则后面的libboost_xxx的版本对应不上。
之后将生成的caffe.pb.cc和caffe.pb.h拷贝至目录(D:\caffe-windows\include\caffe\proto)下:
添加boost的包含目录
C:\Users\MWG\.caffe\dependencies\libraries_v140_x64_py35_1.1.0\libraries\include\boost-1_61
添加其他依赖的包含目录
C:\Users\MWG\.caffe\dependencies\libraries_v140_x64_py35_1.1.0\libraries\include
若加入了预处理的宏定义
USE_OPENCV
CPU_ONLY
添加两个预处理宏,更多预定义的宏添加
则不需要添加cuda的包含目录,否则需要加入cuda的包含目录和库目录,分别为C:\Program Files\NVIDIA GPU Computing Toolkit\CUDA\v8.0\include
和 C:\Program Files\NVIDIA GPU Computing Toolkit\CUDA\v8.0\lib\x64
。
Opencv库自己的电脑已经安装并配置
库目录, VC++目录 -> 库目录 添加
C:\Users\MWG\.caffe\dependencies\libraries_v140_x64_py35_1.1.0\libraries\lib
在编译的时候系统会提示无法打开lib*.lib文件(例如,无法打开文件“libboost_date_time-vc140-mt-1_61.lib”),我的系统中主要是boost中的一些lib。其实这些lib在文件夹中是存在的只是命名的方式不对。将库文件夹中对应的lib文件前面加上lib三个字母就可以了。
例如我的系统中提示找不到libboost_date_time-vc140-mt-1_61.lib,在同一个文件夹中创建一个副本并重新命名为libboost_date_time-vc140-mt-1_61.lib就行了。
还有另外一个,将“boost_filesystem-vc140-mt-1_61.lib”复制一份,并重命名为"libboost_filesystem-vc140-mt-1_61.lib"。
添加caffe.lib的Release版本包含目录,
D:\caffe-windows\scripts\build\lib\Release
并在附加依赖项中加入caffe.lib
Opencv库自己的电脑已经安装并配置
附加依赖项,链接器 -> 输入 -> 附加依赖项 添加
根据 D:\caffe-windows\scripts\build\examples\cpp_classification\Release
目录下的DLL依赖文件名称,在附加依赖中添加对应的lib名。
例如,
总的附加依赖项
caffe.lib
caffeproto.lib
python35.lib
gflags.lib
glog.lib
libprotobuf.lib
libprotoc.lib
opencv_world3411.lib
boost_chrono-vc140-mt-1_61.lib
boost_filesystem-vc140-mt-1_61.lib
boost_python-vc140-mt-1_61.lib
boost_system-vc140-mt-1_61.lib
boost_thread-vc140-mt-1_61.lib
caffehdf5.lib
caffehdf5_hl.lib
caffezlib.lib
libopenblas.dll.a
其中,libprotoc.lib可以不要,或许还有一两个包可以不要,dont mind。
此时已经能够编译成功。
--------------------------------------------------------------漂亮的分界线------------------------------------------------
int main(int argc, char** argv) {
/*
if (argc != 6) {
std::cerr << "Usage: " << argv[0]
<< " deploy.prototxt network.caffemodel"
<< " mean.binaryproto labels.txt img.jpg" << std::endl;
return 1;
}
*/
::google::InitGoogleLogging(argv[0]);
/*
string model_file = argv[1];
string trained_file = argv[2];
string mean_file = argv[3];
string label_file = argv[4];
string file = argv[5];
*/
// mwg
string model_file = "D:/caffeProjects/cifar/cifar10_quick.prototxt";
string trained_file = "D:/caffeProjects/cifar/cifar10_quick_iter_4000.caffemodel.h5";
string mean_file = "D:/caffeProjects/cifar/mean.binaryproto";
string label_file = "D:/caffeProjects/cifar/synset_words.txt";
string file = "D:/caffeProjects/cifar/dog.jpg";
Classifier classifier(model_file, trained_file, mean_file, label_file);
std::cout << "---------- Prediction for "
<< file << " ----------" << std::endl;
按照下面问题5,6修改代码,layer的加入与注册。
下载测试数据,后面链接网盘中目录的 “caffeProjects/cifar”
链接:http://pan.baidu.com/s/1skIfYkH 密码:w69a
无法解析的外部符号 “public: void __cdecl caffe::Blob::FromProto(class caffe::BlobProto const &,bool)”
答:此类问题一般是由于缺失对应的lib包造成的,解决方案为在库目录和附加依赖项中添加进去正确的依赖包,本问题添加caffe.lib即可。
无法打开文件“python35.lib”
答:由于自己的电脑默认python环境不是conda,而是另一个python3.6,所以可能系统无法找到对应的包。解决方案为在库目录和附加依赖项中添加进去正确的依赖包。在目录D:\miniconda3\envs\caffe\libs
下的python35.lib包。
无法解析的外部符号 “public: virtual __cdecl caffe::BlobProto::~BlobProto(void)”
答:此类问题一般是由于缺失对应的lib包造成的,解决方案为在附加依赖项中添加进去正确的依赖包。本问题添加caffeproto.lib即可。
无法解析的外部符号 “__declspec(dllimport) public: class std::basic_string
答:此类问题一般是由于缺失对应的lib包造成的,解决方案为在附加依赖项中添加进去正确的依赖包。本问题添加caffeproto.lib即可。
layer_factory.cpp:62] Check failed: registry.count(type) == 1 (0 vs. 1) Unknown layer type: Input (known types: Convolution, Eltwise, LRN, Pooling, Power, Python, ReLU, Sigmoid, Softmax, Split, TanH)
*** Check failure stack trace: ***
答: 参考博客。 大概是libcaffe.lib是静态库的方式编译的,有一些东西没法使用。解决方案就是,新建一个头文件,例如head.h,将他提示你没有的层的头文件包含进去,在添加类似于extern INSTANTIATE_CLASS(InputLayer);的这句话
后来发现有的层添加了也会报错,那是因为他们没有类似于REGISTER_LAYER_CLASS(Input);这句话。可以想象,
REGISTER_LAYER_CLASS这句话作用就是注册layer。可以添加进去。贴上自己的head.h,添加了使用到的layer。
#include "caffe/common.hpp"
#include "caffe/layers/input_layer.hpp"
#include "caffe/layers/inner_product_layer.hpp"
#include "caffe/layers/dropout_layer.hpp"
#include "caffe/layers/conv_layer.hpp"
#include "caffe/layers/relu_layer.hpp"
#include "caffe/layers/pooling_layer.hpp"
#include "caffe/layers/lrn_layer.hpp"
#include "caffe/layers/softmax_layer.hpp"
namespace caffe
{
extern INSTANTIATE_CLASS(InputLayer);
extern INSTANTIATE_CLASS(InnerProductLayer);
extern INSTANTIATE_CLASS(DropoutLayer);
extern INSTANTIATE_CLASS(ConvolutionLayer);
REGISTER_LAYER_CLASS(Convolution);
extern INSTANTIATE_CLASS(ReLULayer);
REGISTER_LAYER_CLASS(ReLU);
extern INSTANTIATE_CLASS(PoolingLayer);
REGISTER_LAYER_CLASS(Pooling);
extern INSTANTIATE_CLASS(LRNLayer);
REGISTER_LAYER_CLASS(LRN);
extern INSTANTIATE_CLASS(SoftmaxLayer);
REGISTER_LAYER_CLASS(Softmax);
}
之后在classification.cpp
中include该头文件
# include "head.h"
layer_factory.cpp:48] Check failed: registry.count(type) == 0 (1 vs. 0) Layer type Convolution already registered.
答:删掉对应extern INSTANTIATE_CLASS 后面的REGISTER_LAYER_CLASS。