静态编译

来源:互联网 发布:渡口网络破产 编辑:程序博客网 时间:2024/05/16 09:39

一、序言

当一个opencv工程实现之后,我们会面临一个问题,怎么把opencv程序的exe在其他电脑上运行,这个问题已经有很多人遇到过,当然也有很多人给出了博客,介绍了具体的解决方法,具体自己操作时,还是遇到了这样或者那样的小毛病,不过凭借自己根据错误提示解决问题的能力,最后还是把静态编译给编译成功了。

本文介绍几种opencv程序移植到其他电脑运行的方法,一种是动态编译,需要拷贝程序运行需要的dll,也就是-个exe跟着多个dll的模式,这种简单粗暴,但是显得拖拖拉拉,一个程序还得跟着那么多其他文件,所以我们很不推荐。另外一种就是本文主要介绍的静态编译,和之前运行不一样,我们在这使用的不是opencv的lib库,而是staticlib,编译成功之后,程序只需要拷贝一个exe,就可以在其他电脑上运行。

另外介绍一下本文测试程序工作的程序配置 

操作系统Win7IDEVS2010opencv版本opencv2.4.5

二、动态编译

为了做一个全面的总结,在这简单的介绍opencv动态编译的方法。

opencv动态编译需要两部分dll:

(1)opencv库的dll,检查你所引用的h文件,把对应的dll,拷贝过来就行,注意debug和release的不同,当然一般程序发布的话都会用release版本的,因为release版本比debug版本要快10倍有余。

(2)考虑到目标终端有可能没有装vs,所以需要拷贝msvcp110.dll和msvcr110.dll(release下),dll在C:/Windows/System32下。

三、静态编译

静态编译主要的不同就是利用的是H:/Opencv2.4.5/opencv/build/x86/vc11/staticlib文件下的lib,而非H:/Opencv2.4.5/opencv/build/x86/vc11/lib文件夹。具体配置如下:

     1.新建空项目,项目名称Static_Opencv

   2.新建cpp,写入一个简单opencv测试程序:

#include <opencv2/core/core.hpp>#include <opencv2/highgui/highgui.hpp>using namespace cv;void main(){cv::Mat image = cv::imread("img1.png");cv::flip(image,image,1);cv::imwrite("flip.jpg",image);}

    3.新建一个属性管理器

视图-》属性管理器-》Debug-》右键-》添加新项目属性表

  

属性表名称改为PropertySheet_Static_Opencv_debug。

   4.编辑属性表

右键属性表-》属性-》VC++目录-》包含目录,然后添加opencv的h文件目录:

库目录里面添加staticlib文件夹目录

然后C/C++-》代码生成-》运行库-》多线程调试(/MTd),

介绍一下这四个选项,多线程(/MT)为静态链接release模式,多线程调试(/MTd)为静态链接debug模式,多线程dll(/MD)为动态链接release模式,多线程调试DLL(/MDd)为动态链接debug模式。

   5.最后在程序中添加#pragmatic,使用程序调用lib

完整的程序如下:

#include <opencv2/core/core.hpp>#include <opencv2/highgui/highgui.hpp>#pragma comment( lib, "IlmImfd.lib")#pragma comment( lib, "libjasperd.lib")#pragma comment( lib, "libjpegd.lib")#pragma comment( lib, "libpngd.lib")#pragma comment( lib, "libtiffd.lib")#pragma comment( lib, "zlibd.lib")#pragma comment( lib, "opencv_core245d.lib")#pragma comment( lib, "opencv_highgui245d.lib")#pragma comment( lib, "vfw32.lib" )#pragma comment( lib, "comctl32.lib" ) using namespace cv;void main(){cv::Mat image = cv::imread("img1.png");cv::flip(image,image,1);cv::imwrite("flip.jpg",image);}
    最后程序运行会出现很多warning,但是不影响运行,程序大小为7.5M!挺大的,但是一个大程序,总比一个exe跟着多个dll好啊。

6.程序运行结果

原图:

结果图:

四:附加方法1


以下说明,针对于VS2012,其他VS版本,可类比(如VS2013 ,将下面的 VC11 替换成 VC12)。建议使用Everything 搜索软件,当提示缺少哪个库文件时,在开发PC上搜索找到该文件,考到新PC上。

  1. 项目属性 - C/C++ - 代码生成 - 运行库 - 选择“多线程(/MT)”
  2. 编译
  3. copy编译生成的exe文件,复制VS运行所需的三个库: 
    • debug模式复制 \VC\redist\x86\Microsoft.VC110.DebugCRT 文件夹下的三个dll
    • release模式复制 \VC\redist\x86\Microsoft.VC110.CRT 文件夹下的三个dll
  4. 在一台没有安装VS和OpenCV的电脑上运行exe程序,按照提示缺少的库文件从开发的电脑上(opencv\build\x86\vc11\bin)逐个复制到exe程序相同的目录 
    为了省事.可以复制全部OpenCv的运行库:\build\x86\vc11\bin下的所有dll文件 
    • debug 模式: *d.dll 文件
    • release 模式:*.dll 文件

最终的文件夹包含:exe程序、三个vs运行库文件、若干个所需的OpenCV运行库文件

VS 三个运行库分别为: 
- debug 模式 : msvcp110.dll,msvcr110.dll,vccorlib110.dll 
- release 模式 : msvcp110d.dll,msvcr110d.dll,vccorlib110d.dll

Everything 软件下载:http://www.voidtools.com/

五:如何生成能在没有安装opencv库及vs2010环境的电脑上运行的exe文件

项目基本算法已经完成,甲方需要一个可以运行的demo。目前,程序能在自己的电脑上正常运行。移植到其他win7系统上,运行失败。

寻找各种解决办法,baidu找到两个办法:

1.使用静态链接的方法,这种生成的exe太大,放弃。

2.将对应需要的dll拷贝到exe的执行目录下,这种虽然文件多,但是易操作,选择。

我的环境windows7 + Visual Studio 2010 + opencv2.4.7,各种基本的配置省略。

1.打开项目配置页->c/c++->代码生成->运行库,设置成多线程调试DLL(/MD)(release版的程序选择MD,这一步是为了添加程序运行需要的运行库)

2.F7生成exe,然后把对应的dll库拷贝到exe的文件夹下面。将此文件夹作为一个整体发送给甲方。(具体需要拷贝哪些dll库可以使用visual studio的dependents查看,方法如下)

使用dependents查看exe所需要的dll库:

1.开始->所有程序->Microsoft Visual Studio 2010 ->Visual Studio Tools->Visual Studio 2010 命令提示.

2.跳转到exe所在根目录下,输入dumpbin /dependents stabilization_KLT.exe,就会有如图所示结果。

我们需要添加libgsl.dll和四个opencvdll库,除此还需额外添加opencv_ffmpeg247.dll,不然总提示读取视频失败。下面的几个DLL文件在上面步骤一修改运行时库就已经添加了。

实测在其他win7中可以正确运行。




0 0