win10系统 + vs2017 + opencv3.4.15 + cuda11.1 + cmake
注:我本来用的是 opencv3.4.7,然后查了很多教程尝试都未成功,一直报错:
CMake Error: The following variables are used in this project, but they are set to NOTFOUND.
Please set them or make sure they are set and tested correctly in the CMake files:
CUDA_nppi_LIBRARY (ADVANCED)
后来查到原因 可能是新版cuda11.1 对旧版本的 opencv 支持不友好,需要修改一些编译的配置,比如这两个博文中的解决方法:链接1 链接2
但是最终还是没能解决。所以果断放弃了使用 opencv3.4.7 ,更换成 opencv3.4.15,新版本的 opencv 对 cuda11.1 的支持会更好。
1、下载好 opencv-3.4.15 源码、opencv_contrib-3.4.15 源码,并解压;
2、在解压后的 opencv-3.4.15目录中创建目录 build,用于存放编译后的文件;创建 install 目录用于存放最终编译生成的头文件、dll、lib文件;
3、打开cmake,源码目录选择解压后的 opencv-3.4.15 目录,编译目录选择刚刚创建的build目录。点击“Configure”按钮,选择vs2017 、x64,配置成功;
4、编译选项:
(1)WITH_CUDA 勾选上;
(2)OPENCV_EXTRA_MODULES_PATH 选中解压后的 opencv_contrib-3.4.15目录中的 modules 路径;
(3)ENABLE_FAST_MATH 勾选上;
(4)CMAKE_INSTALL_PREFIX 修改为刚刚创建的 install 目录,用于存放生成的头文件、库文件等;
(5)BUILD_opencv_world 勾选上,可将所有的库文件汇总到 opencv_world 这1个库文件中。
5、再次点击“Configure”按钮,成功后再点击“Generate”按钮。
6、在 build 目录中找到 OpenCV.sln,用 vs2017 打开;
7、在生成库文件之前,需要做一件事,修改“python37_d.lib” 为 “python37.lib”; 是因为我生成库文件时(大概过了5个小时),最终报错 “无法打开文件“python37_d.lib””,导致生成失败,很扎心,又要重新生成;具体操作方法:
(1)在 bindings 项目中的外部依赖项中,找到 pyconfig.h 头文件,并打开;
(2)找到如下代码,把 # define Py_DEBUG 屏蔽 :
#ifdef _DEBUG
# define Py_DEBUG
#endif
(3)将 pragma comment(lib,"python37_d.lib") 修改为 pragma comment(lib,"python37.lib")
8、在 vs 中的 “生成” -> “批生成” 中 选择 项目All_BUILD 的 Debug|x64 和 Release|x64,点击生成。【漫长的等待,至少5个小时以上】
9、生成成功后,再在“生成” -> “批生成” 中 选择 项目 INSTALL 的 Debug|x64 和 Release|x64,点击生成 。【这次不需要等待很长时间】
10、然后再 install 目录中,就可以看到生成的 头文件、库文件等;
11、我们只需要 install 目录中生成的即可,其他的文件都可以删除了。把 install 目录名称修改为 opencv3.4.15, 在windows中配置系统环境变量。
新建项目,并配置好刚刚生成的 opencv3.4.15 环境(包含目录、库目录、依赖项),这里就不介绍了,网上很多,而且很简单。
直接上测试程序代码:
#include
#include "opencv2/opencv.hpp"
using namespace std;
using namespace cv;
//#define CUDA_OPENCV
int main()
{
Mat img1 = imread("1.jpg");
Mat img2 = imread("2.jpg");
if (img1.empty() | img2.empty()) {
cout << "Could not open an image!" << endl;
return -1;
}
int len = 10000;
auto start = std::chrono::system_clock::now();
#ifdef CUDA_OPENCV
//Create memory for resorting images on device
cuda::GpuMat d_result, d_img1, d_img2;
//Upload images to device
d_img1.upload(img1);
d_img2.upload(img2);
Mat h_result;
for (size_t i = 0; i < len; i++)
{
cuda::add(d_img1, d_img2, d_result);
}
//Download result back to host
d_result.download(h_result);
#else
Mat h_result;
for (size_t i = 0; i < len; i++)
{
cv::add(img1, img2, h_result);
}
#endif // CUDA_OPENCV
auto end = std::chrono::system_clock::now();
cout << "Times:" << std::chrono::duration_cast(end - start).count() * 1.0f / len << "ms";
imshow("Image1", img1);
imshow("Image2", img2);
imshow("Result", h_result);
waitKey();
system("pause");
return 0;
}
程序中包含了 cpu 运行和 gpu 运行,直接看下运行耗时:
1、cpu 运行每次耗时:
2、 gpu 运行每次耗时:
结论:从上面测试中可以看到,cuda opencv 运行有着明显的效率优势。