OPENCV Learning Notes (ii)-cv::mat learning

Source: Internet
Author: User
Tags data structures image processing library scalar

Because in writing an image of the data structure, found oneself only know cvmat, unexpectedly still have mat data structure, really ignorant, see so many programs, seemingly did not see this structure. It's possible that those programs are examples of older versions, which were added after 2.0, so I have to follow them. The following is your own learning experience ....

Introduction of Mat

OpenCV was built on the C language interface when it first appeared in 2001. To store images in memory (memory), the C-language structure, called Iplimage, is still present in most of the older tutorials and teaching materials. However, this method must accept all the deficiencies of C language, which is the biggest disadvantage of manual memory management, based on the user to open up and destroy memory. While for small programs, manual management

Introduction of Mat

OpenCV was built on the C language interface when it first appeared in 2001. To store images in memory (memory), the C-language structure, called Iplimage, is still present in most of the older tutorials and teaching materials. However, this method must accept all the deficiencies of C language, which is the biggest disadvantage of manual memory management, based on the user to open up and destroy memory. While it's not a problem to manually manage memory for small programs, once the code gets bigger and bigger, you need to get more involved in the problem rather than focus on your development goals.

Fortunately, C + + appears and brings the concept of class, which gives the user another option: Automatic memory management (loosely speaking). This is good news, if C + + is fully compatible with C, this change will not cause compatibility problems. To this end, OpenCV introduced a new C + + interface in version 2.0, using automatic memory management to give a new way to solve the problem. With this approach, you don't have to tangle with managing memory, and your code will become concise (write less). But the only disadvantage of the C + + interface is that many embedded development systems currently support only the C language. So, when the target is not this development platform, there is no need to use the old method (unless you are a trouble-free masochist).

The first thing you need to know about Mat is that you don't have to manually (1) Open space for it (2) to release space immediately if you don't need it. But it's OK to do it manually: Most OPENCV functions still manually open up space for the output data. When passing an already existing Mat object, the open matrix space is reused. That is, each time we use the right size memory to complete the task.

Basically, Mat is a class that consists of two data parts: a matrix header (including matrix dimensions, storage methods, storage addresses, and so on) and a pointer to a matrix that stores all pixel values (depending on the different matrices of the selected storage method can be different dimensions). The size of the matrix head is a constant value, but the size of the matrix itself varies according to the image, usually a number of orders of magnitude larger than the size of the matrix head. Therefore, when passing images in a program and creating copies, the overhead is caused by the matrix, not the information header. OpenCV is an image processing library, which includes a large number of image processing functions, in order to solve the problem is usually to use a library of multiple functions, so in the function of passing images is commonplace. And don't forget that we're talking about a very computational image processing algorithm, so we shouldn't copy large images unless we have to, because it slows down the program.

second, the basic operation of Mat

Here is an example to explain the basic operation of Mat

#include <cv.h> #include 

for MAT data structures, be aware of the image processing:

The memory allocation of the output image in the OpenCV function is done automatically (if not specifically specified). You do not need to consider memory release issues when using the OpenCV C + + interface. the assignment operator and the copy constructor (ctor) copy only the header of the message. Use the function clone () or copyTo () to copy a matrix of an image

third, scanning the image method

    

#include <cv.h> #include  int i=0;i ) {uchar* data = img_gray.ptr<uchar> (i); 
		for (int j=0;j (0);//Fetch first pixel pointer for (int i=0;i<nc;i++)//Traverse all elements {data_2[i] = 255;
	//Mode three-pointer scan uchar* data_3 = img.data;//single element img.at<uchar> (0,0) = 0; for (int i=0;i::iterator it = img.begin<vec3b> ();  
	Mat_<vec3b>::iterator itend = img.end<vec3b> ();  
			 for (; it!=itend; it++) {//Assign values to each channel (*it) [0] = 200; (*it) 
			 [1] = 200; (*it) 
	[2] = 200;
	//test, view the results according to their own selection Namedwindow ("Sorce", window_autosize);

	Namedwindow ("result", window_autosize);
	Cv::imshow ("Sorce", IMG);

	Cv::imshow ("result", Img_gray);
	Waitkey (0);

return 0; }


The above is the synthesis of http://blog.csdn.net/yang_xian521/article/details/7182185#, the following is its blog, as the blogger said, data_3 = Img.data + i* Img.step + J * img.elemsize ();, int i=0;i

1. Access to a single pixel value

The most common method is to

[CPP] view plain copy print?  Img.at<uchar> (i,j) = 255; Img.at<vec3b> (I,J) [0] = 255;

Img.at<uchar> (i,j) = 255;
Img.at<vec3b> (I,J) [0] = 255;


If you think the at operation is too unwieldy to use the mat class, consider using the lightweight Mat_ class and using overloaded operators () to implement the element-taking operation.

[CPP] view plain copy print? Cv::mat_<uchar> im2= img; IM2 refers to Image im2 (50,100) = 0; Access to row and column 100

Cv::mat_<uchar> im2= img; IM2 refers to Image
   im2 (50,100) = 0;//access to row and column 100


2. Scan a picture with a pointer

For a scan of an image, using at is not very good, or is the use of pointers to the operation of more recommended. Let me introduce one of the last mentioned

[CPP] view plain copy print?          for (int j=0; j<nl; J + +) {uchar* data= image.ptr<uchar> (j);          for (int i=0; i<nc; i++) {data[i] = 255; }  }

for (int j=0; j<nl; j + +)
{
        uchar* data= image.ptr<uchar> (j);
        for (int i=0; i<nc; i++)
       {                 
                  data[i] = 255;
        }
}


The idea of a more efficient scan of a continuous image might be to think of W*h's clothing image as a one-dimensional array of 1* (w*h), a bit of a miracle, to use the Iscontinuous function to determine whether the pixels in the image are filled with the following methods:

[CPP] view plain copy print?  if (img.iscontinuous ()) {NC = Img.rows*img.cols*img.channels ();  } uchar* data = img.ptr<uchar> (0);  for (int i=0; i<nc; i++) {data[i] = 255; }

if (img.iscontinuous ())
{
        NC = Img.rows*img.cols*img.channels ();
}
uchar* data = img.ptr<uchar> (0);
for (int i=0; i<nc; i++)
{
        data[i] = 255;
}


The lower-level pointer operation is to use the data pointer in mat, which I call violent youth, using the following methods:

[CPP] view plain copy print?  uchar* data = Img.data; Img.at (i, j) data = Img.data + I * img.step + J * Img.elemsize ();

uchar* data = Img.data;
Img.at (i, j)
data = Img.data + I * img.step + J * Img.elemsize ();


3. Iterator scan image with iterator

Similar to the iterator in C++stl, the mat iterator is compatible with it. It's matiterator_. The Declaration method is as follows:

[CPP] view plain copy print? Cv::matiterator_<vec3b> it;

Cv::matiterator_<vec3b> it;


Or is:

[CPP] view plain copy print? Cv::mat_<vec3b>::iterator it;

Cv::mat_<vec3b>::iterator it;


The methods for scanning images are as follows:

[CPP] view plain copy print?  Mat_<vec3b>::iterator it = img.begin<vec3b> ();  Mat_<vec3b>::iterator itend = img.end<vec3b> ();  for (; it!=itend; it++) {(*it) [0] = 255; }

Mat_<vec3b>::iterator it = img.begin<vec3b> ();
Mat_<vec3b>::iterator itend = img.end<vec3b> ();
for (; it!=itend; it++)
{
         (*it) [0] = 255;
}


4. The efficient Scan Image plan summary

Or use the GetTickCount, gettickfrequency function we used before to test the speed. Here I will not enumerate the results of my test, directly on the conclusion. The test found that a good writing style can increase the speed of 50%. To reduce the time it takes to run a program, the necessary optimizations include the following:

(1) Memory allocation is a time-consuming work, optimization;

(2) The repeated calculation of the value in the loop is a time-consuming work, optimized;

[CPP] view plain copy print?  int NC = Img.cols * Img.channels ();  for (int i=0; i<nc; i++) {...} for (int i=0; I

int NC = Img.cols * img.channels ();
for (int i=0; i<nc; i++)
{...}
for
(int i=0; I


The latter has a much slower pace than the former.

(3) The use of iterators will also be slow, but the use of iterators can reduce the occurrence of program errors, consider this factor, you can optimize

(4) At operation is much slower than the operation of the pointer, so for discontinuous data or single point processing, you can consider at operation, for a large number of consecutive data, do not use it

(5) Scanning the continuous image may be the w*h clothing image as a 1* (w*h) of a one-dimensional array this method can also improve the speed. Short loops are more efficient than long loops, even if their operands are the same

These optimizations may not be obvious to the speed of the program, but they are a good programming strategy to get the speed improvement, I hope we can adopt more.

There is also the use of multithreading can also improve the speed of running efficiently. OpenMP and TBB are two popular apt, but for multithreading things, I was a little confused, hehe 5. Assignment of whole row pixel values

For whole rows or whole columns of data, consider this method of handling

[CPP] view plain copy print?  Img.row (i). Setto (Scalar (255)); Img.col (j). Setto (Scalar (255));

Img.row (i). Setto (Scalar (255));
Img.col (j). Setto (Scalar (255));


This section will introduce so many Raiders first ~ hope you like

reference materials

1.http://www.opencv.org.cn/opencvdoc/2.3.2/html/doc/tutorials/core/mat%20-%20the%20basic%20image% 20container/mat%20-%20the%20basic%20image%20container.html

2http://blog.sina.com.cn/s/blog_73ee929c01010yor.html

           


Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.