尧图网站设计 尧图网站设计YAOTU DESIGN
ARTICLE DETAIL

资讯详情

深耕网站设计与一线实操的经验洞察。

Windows下编译OpenCV GPU版:CUDA加速与VS2019环境配置全指南

Windows下编译OpenCV GPU版:CUDA加速与VS2019环境配置全指南 简介这是一套基于微软Visual Studio 2019集成开发环境编译的OpenCV 4.9.0 GPU版本构建产物面向Windows平台上使用C开发图像处理与计算机视觉应用的工程师封装了动态链接库与静态链接库可直接在工程中引入头文件并链接使用无需自行配置编译环境。压缩包包含六百七十三个文件其中头文件占大多数HPP有六百零一个H有五十六个覆盖图像处理、特征检测、深度学习等模块的接口另有四个CMake配置脚本、六个可执行程序、四个动态链接库和两个静态链接库用于编译、运行与调试。整体约六十九点九兆字节按目录分类存放。目前已有六百零二人下载学习。借助GPU并行计算可提升图像预处理、特征提取和模型推理的速度节省开发调试时间适合实时性要求高的视觉工程。1. 为什么要自己编译OpenCV的GPU版本先说实话OpenCV官网下载页面提供的预编译包默认是不包含CUDA支持的。也就是说你从官网拉下来的Windows安装包即使代码里写了cv::cuda::GpuMat运行时也会直接报错因为底层库根本没编译GPU模块。这个问题我在第一次接触OpenCV GPU开发时踩得结结实实——折腾了半天的代码结果连库都没带GPU模块心态直接崩了。所以如果你要在Windows上用GPU加速图像处理、DNN推理或者做视频分析的实时管线自己编译一个GPU release版本几乎是绕不开的路。简单解释一下这套方案的组成OpenCV 4.9.0当前比较稳定的大版本dnn模块对CUDA的支持比4.5.x时代成熟很多cv::dnn::Net支持设置CUDA后端和目标不需要再自己写自定义层。VS2019Windows下最主流的C编译器环境VC142工具集和CUDA 11.x的适配最有默契。VS2022虽然也能用但如果你现有项目还挂在VS2019上就别折腾着换。GPU/CUDA核心是NVIDIA的CUDA工具包和cuDNN。OpenCV的GPU模块即opencv_world490.dll中的cuda相关部分全部依赖CUDA runtime来调用显卡计算资源。这套编译方案适合什么人适合四类人一是要做实时图像处理但没有现成GPU基础设施的开发者二是需要用OpenCV的dnn模块跑深度学习模型、嫌弃CPU推理太慢的人三是需要把OpenCV嵌入到已有的VS2019项目里、对运行效率有硬性要求的人四是自己维护算法库、需要自定义OpenCV模块的进阶用户。看这篇博文你会完整走一遍从环境准备、CMake配置、VS编译到测试验证的全过程。所有参数、版本号、踩坑点我都会标注清楚照着做基本能一次成功。2. 编译前的环境准备与版本匹配2.1 版本对照表确定不会翻车的组合编译OpenCV这种体量的项目版本匹配是第一优先级。不是说新的就好而是要确保你本机的CUDA版本、显卡驱动版本、VS版本能互相认识。我实测稳定的一套组合如下组件推荐版本备注操作系统Windows 10/11 64位不支持32位系统玩CUDA编译器Visual Studio 2019 16.11.x必须是VC142工具集CMake3.20以上推荐3.26/3.27太老的CMake会连CUDA都探测不到Python可选3.8-3.11如果不需要python接口可以忽略CUDA Toolkit11.8最稳12.x也可以但某些型号显卡需要打补丁cuDNN8.6.0或8.9.x需和CUDA版本对应显卡驱动最近两年的版本即可560.x以后的驱动对CUDA 11.8依然兼容这里特别说一句CUDA不一定追新。我用过CUDA 12.2编译OpenCV 4.9.0过程也能过但在dnn模块跑onnx模型时出现过一次奇怪的精度问题切回CUDA 11.8后一切正常。如果你的显卡是RTX 30系或更早的10系、20系建议直接选CUDA 11.8省心。2.2 安装CUDA和cuDNN的注意点CUDA Toolkit直接去NVIDIA官网下载exe安装包就行安装路径建议用默认的C:\Program Files\NVIDIA GPU Computing Toolkit\CUDA\v11.8。在安装过程中不要勾选Nsight Visual Studio Edition如果你不需要用Nsight调试的话因为有时候它会和VS2019的扩展管理器冲突导致后续编译莫名其妙报错。还要注意环境变量。CUDA安装完成后CUDA_PATH和CUDA_PATH_V11_8系统环境变量是自动配置好的C:\Program Files\NVIDIA GPU Computing Toolkit\CUDA\v11.8\bin也会加到Path里。你可以在命令行运行一下nvcc --version如果能正常输出版本信息说明CUDA工具链没问题。cuDNN的解压安装比较特殊。它不是一个安装包而是一个压缩包解压后里面有bin、include、lib三个目录。你要做的是把这三个目录里的内容分别拷贝到CUDA安装目录对应的同名目录下。注意是把内容拷进去不是把整个目录替换掉。2.3 必须准备的依赖库OpenCV编译时还会自动检测一些第三方库比如IPPICVIntel的并行图像处理库CMake配置时会自动下载如果下载失败编译也能继续但速度会稍慢一些。FFmpeg用于视频解码的库CMake会尝试下载预编译包。如果你不需要处理视频文件可以不管它如果需要视频处理建议确保网络通畅让CMake顺利下载。EigenOpenCV某些模块的数学库依赖非必需。TBBIntel线程构建模块可以启用但不是必需。在实际编译过程中常用的做法是让CMake自动下载顺便准备一个代理或者多试几次这里不涉及任何违规工具只是网络通畅问题。因为OpenCV的CMake脚本会自动从GitHub或SourceForge拉取依赖包网络不稳定时容易失败。3. CMake配置整个流程的胜负手3.1 获取源码并建立编译目录先到OpenCV官网opencv.org下载Release版本的源码包我建议下载Sources版本也就是opencv-4.9.0.zip。不要下载Windows版本的那个预编译exe那个对我们没用。源码解压到某个目录比如D:\opencv\opencv-4.9.0。注意源码路径中千万别出现中文或空格这会导致CMake阶段直接报错而且报错信息还特别隐晦很难排查。然后创建一个编译输出目录比如D:\opencv\build_gpu。为什么要单独建目录因为CMake的构建文件会非常杂乱如果直接编译在源码目录里后续想重新配置或者更新源码会非常痛苦。干净分离出了问题直接删掉build目录重来源码不受影响。3.2 打开CMake GUI并配置关键选项打开CMake GUI在Where is the source code里填D:/opencv/opencv-4.9.0在Where to build the binaries里填D:/opencv/build_gpu然后点击Configure。第一次Configure时CMake会让你选择生成器。选择Visual Studio 16 2019平台如果是64位系统就选x64。这一版本选择特别关键如果你选错了平台后面VS编译时会出现一堆链接错误。Configure完成后你会看到大量红色的配置项。这时候要重点修改以下开关和参数BUILD_opencv_world ON # 把所有的模块编译成一个opencv_world490.dll链接时只认一个lib文件省心 WITH_CUDA ON # 启用CUDA支持这是核心开关 WITH_CUDNN ON # 启用cuDNN支持 OPENCV_DNN_CUDA ON # 让dnn模块支持CUDA后端跑深度学习模型就靠这个 BUILD_CUDA_STUBS OFF # 不编译CUDA存根文件 CUDA_ARCH_BIN 你的显卡计算能力 # 例如8.6对应RTX 3060/3070/30807.5对应RTX 20806.1对应GTX 1060 CUDA_FAST_MATH ON # 启用在CUDA核心数学函数中使用快速数学模式图像处理这类对精度不极端敏感的推荐打开 WITH_OPENGL ON # 如果需要显示窗口加速建议打开 WITH_OPENCL OFF # 其实OpenCL和CUDA是两套体系如果你不使用AMD显卡加速关掉可以减少潜在冲突 BUILD_EXAMPLES OFF # 官方示例代码占了编译时间的大头不搞研究的话先关掉 BUILD_TESTS OFF # 同理测试代码也不需要编 BUILD_PERF_TESTS OFF # 性能测试代码不需要这里最核心的是CUDA_ARCH_BIN。你可以按显卡型号去查计算能力NVIDIA官网有完整的表格搜索NVIDIA CUDA GPUs Compute Capability即可也可以在命令行运行nvidia-smi右下角能看到你显卡的CUDA版本但不能直接看到计算能力。靠谱的方法是去查显卡型号比如RTX 3060是8.6你直接填8.6即可。3.3 检查CUDA相关配置项Configure完成之后搜索框里搜一下CUDA看看以下的内容是否正确CUDA_TOOLKIT_ROOT_DIR应该指向C:/Program Files/NVIDIA GPU Computing Toolkit/CUDA/v11.8如果不对手动改。CUDA_nvcc_RUNTIME_LIBRARY保持默认Shared即可。CUDNN_INCLUDE_DIR和CUDNN_LIBRARY需要你手动定位到cuDNN的路径。比如D:/cudnn-8.6.0-windows10-x64/cudnn/include和.../cudnn/lib/x64/cudnn.lib。搜索CUDNN如果路径没自动填上就手动指定。这一步容易漏漏了的话虽然CUDA能用但dnn模块的cuDNN加速就没了推理速度会慢不少。设置完这些之后再次点击Configure直到没有红色报错项然后点击Generate。Generate成功会生成OpenCV.sln解决方案文件位置在build目录下。3.4 CMake配置常见报错说一下我遇到的几个典型CMake阶段报错以及怎么处理报错1CMake找不到CUDA编译器CUDA_nvcc not found原因CMake版本太老或CUDA环境变量没配置。解决确认nvcc --version能正常运行然后升级CMake到3.26左右。报错2CUDNN路径无效原因cuDNN版本与CUDA版本不匹配或者指定的include路径没有cudnn.h。解决下对应版本的cuDNN确保cudnn.h和cudnn.lib路径正确。报错3下载IPPICV或者其他依赖包超时原因网络问题。解决可以多试几次Configure让CMake继续下载。也可以手动从网上下载对应依赖包放到build目录的downloads文件夹里路径会在报错信息里明确给出。4. VS2019编译Release版本过程与避坑4.1 编译选项设置用VS2019打开D:\opencv\build_gpu\OpenCV.sln。打开之后你会在解决方案管理器里看到一大堆项目项目数量取决于你勾选的模块数量。首先把解决方案配置从Debug切换到Release解决方案平台保持x64。然后右键CMakeTargets下的ALL_BUILD项目选择生成。注意编译之前先确认你的方案里INSTALL项目也要生成。可以在ALL_BUILD上右键选生成生成完毕之后再对INSTALL项目右键生成。这样才会自动把编译好的dll、lib、头文件统一拷贝到build/install目录下。4.2 编译时长与内存占用编译GPU版本比CPU版本慢不少。官方预编译CPU版本在好的机器上大概20分钟GPU版本正常要40到60分钟取决于CPU核心数。我的机器是i7-12700 32GB内存16核20线程编译全程大概45分钟。如果你留意任务管理器编译期间会用满所有核心内存占用大约8-12GB。所以8GB内存的机器建议别同时开太多东西否则容易编译到一半就崩。编译过程中VS的输出窗口会不断滚动。你只需要关注最后是否显示已完成生成和0个错误。如果中途报错通常是因为依赖库缺失或显卡架构设置不对。4.3 常见编译错误与解决办法我把踩过的坑和解决办法直接整理成表错误现象原因解决方案编译时报C2131或C2084等奇怪的编译器错误某些源文件和后装的Windows SDK版本冲突在VS2019安装器中更新或降级Windows SDK到10.0.19041.0或更高链接时找不到cudnn.libcuDNN路径没配置正确或没重新Configure回到CMake重新检查CUDNN路径重新Generate之后清理解决方案再生成报fatal error LNK1104: cannot open file opencv_world490d.lib你可能在Debug模式下链接了Release库或反之确认解决方案配置是Release然后确认链接器附加依赖项里写的是opencv_world490.lib而不是带d的库生成时提示MSB3723说CUDA架构不支持显卡计算能力填错了确认CUDA_ARCH_BIN和你实际显卡匹配比如RTX 3090是8.6不要填9.0编译中内存爆掉VS崩溃build并行太多内存不够在VS中减少并行项目数工具 - 选项 - 项目和解决方案 - 生成并运行 - 最大并行项目数改为2或44.4 安装Install环节INSTALL项目生成完毕之后你会在D:\opencv\build_gpu\install目录下看到如下结构install/ ├── include/ │ └── opencv2/ ├── x64/ │ └── vc16/ │ ├── bin/ │ │ ├── opencv_world490.dll │ │ ├── opencv_videoio_ffmpeg490_64.dll │ │ └── ... │ └── lib/ │ └── opencv_world490.lib这些就是要用的头文件和库文件。下一步把它拷贝到项目里或者把路径加到环境变量让所有项目都能访问。我个人习惯直接在系统环境变量Path里加上D:\opencv\build_gpu\install\x64\vc16\bin这样所有项目运行的时候都能找到dll。5. 验证GPU版本是否生效5.1 编写测试代码编译完成并不代表一切OK一定要写一段验证代码确认GPU模块真的被激活了。我用的是最简单的测试查看OpenCV版本、CUDA设备数量、设备的名称和显存大小。#include opencv2/opencv.hpp #include opencv2/core/cuda.hpp #include iostream int main() { std::cout OpenCV version: CV_VERSION std::endl; int deviceCount cv::cuda::getCudaEnabledDeviceCount(); std::cout CUDA enabled devices: deviceCount std::endl; if (deviceCount 0) { cv::cuda::setDevice(0); cv::cuda::DeviceInfo devInfo(0); std::cout Device name: devInfo.name() std::endl; std::cout Total memory: devInfo.totalMemory() / (1024.0 * 1024.0) MB std::endl; std::cout Compute capability: devInfo.majorVersion() . devInfo.minorVersion() std::endl; } // 测试基本GPU图像处理 cv::Mat cpuMat cv::Mat::ones(512, 512, CV_8UC3); cv::cuda::GpuMat gpuMat; gpuMat.upload(cpuMat); cv::cuda::GpuMat result; cv::cuda::cvtColor(gpuMat, result, cv::COLOR_BGR2GRAY); cv::Mat back; result.download(back); std::cout GPU cvtColor test: back.size() back.type() std::endl; return 0; }5.2 配置VS2019项目新建一个空的C控制台项目然后做三件事配置包含目录项目属性 - VC 目录 - 包含目录添加D:\opencv\build_gpu\install\include。配置库目录库目录添加D:\opencv\build_gpu\install\x64\vc16\lib。配置附加依赖项链接器 - 输入 - 附加依赖项添加opencv_world490.lib。然后别忘了是Release x64配置。编译运行后你能在控制台看到类似这样的输出OpenCV version: 4.9.0 CUDA enabled devices: 1 Device name: NVIDIA GeForce RTX 3060 Total memory: 12288 MB Compute capability: 8.6 GPU cvtColor test: 512x512 CV_8UC1看到CUDA enabled devices: 1和你的显卡型号就说明GPU版本编译成功并生效了。5.3 用dnn模块验证GPU推理如果你想进一步确认dnn模块能调用CUDA可以把一个onnx模型用GPU跑一次推理。OpenCV dnn设置CUDA后端的代码很简单cv::dnn::Net net cv::dnn::readNetFromONNX(model.onnx); net.setPreferableBackend(cv::dnn::DNN_BACKEND_CUDA); net.setPreferableTarget(cv::dnn::DNN_TARGET_CUDA);这两行设置好如果推理能正常出结果说明dnn的CUDA加速已经生效。6. 后续使用中的注意事项与个人体会编译完不等于完全放心实际使用中还有几个点值得留意1. 别忘了拷贝dll到可执行目录很多人在自己机器上跑没问题换台电脑或者发给同事就跑不起来了通常是因为dll没带齐。opencv_world490.dll是必须的如果你用到了视频处理opencv_videoio_ffmpeg490_64.dll也建议一并拷贝。再如果用到dnn模块加载模型可能还会依赖cudnn_ops64_8.dll、cudnn_cnn_infer64_8.dll这些CUDA运行库。最简单的做法是给每个项目建一个dll目录统一拷贝一份。2. Debug和Release的库不要混用OpenCV编译出来的库是分Debug带d后缀的opencv_world490d.lib和Releaseopencv_world490.lib两套。如果项目是Debug配置却链接了Release库编译能过但运行时会不定时崩溃反正是玄学问题排查时绝对让你怀疑人生。我的做法是如果不需要断点调试OpenCV内部逻辑就让整个解决方案都用Release配置如果确实需要Debug调试自己的代码那就额外花时间把Debug版本也编译出来。3. 后续想重新编译一定要清理干净换CUDA版本或者CMake版本后直接重新Configure有时会出各种奇怪问题。我的习惯是把build目录整个删掉从头开始Configure。也就多花10分钟换来的是稳定可靠。4. 多版本共存的办法如果你也还在用CPU版OpenCV比如某个老项目依赖3.x版本不想被覆盖可以这样做把GPU版本装到D:\opencv\gpuCPU老版本留在原来的路径项目中通过具体的include和lib路径来切换而不是全依赖环境变量。这样几个项目同时维护也不冲突。我个人编译这套环境最深的体会就是CMake配置这一步千万别赶时间每一个开关背后都有它的意义填错了后面就要花几倍时间排查。还有一个经验是编译之前把杀毒软件或Windows Defender对build目录的实时防护临时关一下虽然这只是一个很小的细节但它会显著减少编译失败的概率。如果你需要进一步扩展比如把OpenCV的contrib模块如opencv_contrib里的xfeatures2d、aruco等也编进去只需要在CMake里把OPENCV_EXTRA_MODULES_PATH指向contrib源码的modules目录重新Configure和编译即可。整个流程走通一次之后后面所有基于VS2019的OpenCV开发都会顺很多。本文还有配套的精品资源点击获取
返回列表