https://img-blog.csdnimg.cn/32db9ce43ef64316a2e37a31f4cee033.gif
编程小鱼酱yu612.com,点击前往

1.10--OpenCV Introduction

一、OpenCv   Introduction

OpenCV 使用BSD协议

官方地址:http://opencv.org/

官方下载地址:http://docs.opencv.org/

 

OpenCV有自己的模块结构,这意味着包含多个共享或静态库,以下是可以获取的模块

Corefunctionality组合的模块,定义了的基本数据结构,包括多维数矩阵和被所有其他模块使用的基本使用的功能。

mageprocessing:一个图像处理模块包括线性和非线性的图像过滤,图像几何变换(调整、仿射和,透视弯曲,一般的基础变换)

         video:视频分析模块,包括运动估计、背景减法,和对象跟踪算法。

·             calib3d -基本的多视图几何算法 ,单体和立体相机标定,物体定位,立体通信算法,三维建筑元素

features2d显著特征探测器,描述符合描述匹配器

objdetect:检测的对象和预定义的类的实例(forexample, faces, eyes, mugs, people, cars, and so on).

highgui一个易于使用的界面简单UI功能

VideoI/O: 一个易于使用的接口来视频捕获和视频编解码器。

gpuGPU-accelerated不同OpenCV的算法模块

 

一些其他辅助模块,FLANN和谷歌测试包装,Python绑定等等。

 

 

二、API概念:

文档的进一步章节描述每个模块的功能,但首先,一定要熟悉所使用的通用API概念

 

cv Namespace

所有的 OpenCV和函数都放置在了 cvnamespace中。因此从代码访问此功能,用cv:: 指示语或者用 usingnamespace cv 指示语

 

 

#include "opencv2/core.hpp"

...

cv::Mat H = cv::findHomography(points1, points2,CV_RANSAC, 5);

...

 

 

Or

 

#include "opencv2/core.hpp"

...

cv::Mat H = cv::findHomography(points1, points2,CV_RANSAC, 5);

...

 

一些当前或未来的OpenCV外部名称可能与STL冲突或其他库,在这种情况下,使用显式的名称空间说明符解决名称冲突use explicit namespace

 

 

自动内存管理 

  OpenCV自动处理所有内存

  首先std::vector, Mat,和其它被函数应用的 数据结构体被函数和方法应用并且带有销毁者(销毁者指的是消除潜在内存当需要的时候)。这就意味着,Mat销毁者不会经常的释放内存。他们将会共享数据。一个destructor消减矩阵的引用计数数据缓存。这块缓存被释放,当且仅当引用计数为0的时候。那是,当没有其它结构引用相同的内存的时候。

相同地,当一个 Mat单例被拷贝,没有真实的数据仅仅是拷贝。反而,引用计数是增加记忆的。那就是有一个其它的拥有者有这块数据。

也有Mat::clone方法,创建一个完整的拷贝矩阵数据。看接下来的例子:

 

// create a big 8Mb matrix

Mat A(1000, 1000, CV_64F);

// create another header for the same matrix;

// this is an instant operation, regardless of the matrixsize.

Mat B = A;

// create another header for the 3-rd row of A; no datais copied either

Mat C = B.row(3);

// now create a separate copy of the matrix

Mat D = B.clone();

// copy the 5-th row of B to C, that is, copy the 5-throw of A

// to the 3-rd row of A.

B.row(5).copyTo(C);

// now let A and D share the data; after that themodified version

// of A is still referenced by B and C.

A = D;

// now make B an empty matrix (which references no memorybuffers),

// but the modified version of A will still be referencedby C,

// despite that C is just a single row of the original A

B.release();

// finally, make a full copy of C. As a result, the bigmodified

// matrix will be deallocated, since it is not referencedby anyone

C = C.clone();

 

你能看到Mat 和其它基础数据结构是单一的。但是什么是高级的类或是甚至用户数据类型

被创建带有引用计数管理呢?对他们来说,OpenCV提供了指针模板类,那就和std::shared_ptrC++ 11

里面的相近。所以,而不是用

 

T* ptr = new T(...);

 

你可以用

 

Ptr<T> ptr(new T(...));

 

 


自动分配输出数据

        OpenCV自动重新分配内存的,  以及大部分时间自动分配内存输出函数参数。所以,如果一个函数有一个或是多个输入数组

(cv::Mat instances) 和一些输出的数组,这些数组是自动释放和分配内存的.输出数组的大小和类型,是由输入的数组大小和类型决定的。如果被需要,函数带有额外的参数(帮助解决输出的数组属性)

        

 

Example:

#include "opencv2/imgproc.hpp"

#include "opencv2/highgui.hpp"

using namespace cv;

int main(int, char**)

{

VideoCapture cap(0);

if(!cap.isOpened()) return -1;

Mat frame, edges;

namedWindow("edges",1);

for(;;)

{

cap >> frame;

cvtColor(frame, edges, COLOR_BGR2GRAY);

GaussianBlur(edges, edges, Size(7,7), 1.5, 1.5);

Canny(edges, edges, 0, 30, 3);

imshow("edges", edges);

if(waitKey(30) >= 0) break;

}

return 0;

}

 

 

数组框架是自动分配的 通过 >> 运算符 当video的帧率 和 位深度 被 video模块捕捉

数组的边界是自动分配的 通过 cvtCOlor函数。它有相同的大小和为书读作为输入的数组。

通道的数量是1 因为在第一次 执行循环的时候 ,所有下一个video 帧有相同的分辨率。

如果你以某种方法改变video分辨率,数组会自动释放。

 

 

这项技术的关键是Mat::create方法。它会带来要求的数组大小和类型。如果数组准备有指定的

大小和类型,这个方法做不了什么。否则它会释放之前的分配的内存。,如果任何(这部分包括引用计数和比较引用计数为0的),并且然后分一个按照需要的大小分配新的内存。大部分函数调用

Mat::create 方法为了输出数组。并且自动释放输出的数据被应用。

 

一些明显的异常从 这个约束cv::mixChannels,cv::RNG::fill,并且一小部分其它的函数和方法。他们将不会分配输出的数组,所以你可以提前自己做。

 

 

 

 

 

 

 饱和度算法

    作为一个计算机视觉库,opencv处理很多像素图片,它们经常是组合编码,8 或是 16位 每个通道,

形式,从而有一个有限的值范围。此外,某些操作图像,比如颜色空间转换,亮度/对比度调整,锐化,复杂的插值(bi-cubic兰索斯)能产生可用的范围值.如果你只是存储最低8(16)位这将导致视觉工件和可能影响进一步的图像分析。为了解决这个问题,使用所谓的饱和算法。例如,存储 R,这个操作的结果,对于一个b位图片,你可能找到相近的值在0..255范围内。

I(x,y)=min(max(round(r),0),255)

 

同样的规则适用于8位有符号,有符号的16位和无符号类型。在库到处都使用这个语义.c++代码,它是使用saturate_cast< >类似于标准c++操作.见下文的实现上面提供的公式:

I.                   at<uchar>(y, x) =saturate_cast<uchar>(r);

uchar是个OpenCV 8位无符号整数类型。在优化的SIMD代码中,诸如paddusb SSE2指令,使用packuswb等等。他们帮助实现完全相同的行为如c++代码。

 

Note:

色饱和度不会被应用,当 int32位的时候


 

 

错误处理

OpenCV使用异常信号危险错误。当输入的数据有一个正确的格式并且属于指定的值范围,但是算法不能成功因为有这些理由

(例如,优化算法不集中),它的返回一个特殊的错误码(代表,仅是一个布尔变量)。

异常可以被实例 cv::Exception或是它的派生类处理。在它的转换,cv::Exception 是一个派生于std::exception.所以它能被优雅的处理,通过在代码使用其它         C++库组件。

异常抛出使用CV_Error(errcode, description)

try

{

... // call OpenCV

}

catch( cv::Exception& e )

{

const char* err_msg = e.what();

std::cout << "exception caught: " <<err_msg << std::endl;

}



多线程 和可重用的

         当前的 OpenCV实现是可重用的。那就是,相同的功能,相同的常量方法类的实例,或相同的不是常量的方法,都可以从不同的线程被调用。同样,相同的cv::Mat可以被使用在不同的线程。因为引用计数操作的特殊结构,自动释放。


 

 未完,待续~~~~~~~

 

 

 

 

 

 


posted @ 2017-03-22 20:55  鱼酱  阅读(208)  评论(0编辑  收藏  举报

https://img-blog.csdnimg.cn/32db9ce43ef64316a2e37a31f4cee033.gif
编程小鱼酱yu612.com,点击前往