Create convex edges from a sequence or array of point sets

Source: Internet
Author: User

[Cpp]
# Include <cv. h>
# Include # Include <stdlib. h>
 
# Define ARRAY 0
 
Int main ()
{
IplImage * img = cvCreateImage (cvSize (500,500), 8, 3 );
CvNamedWindow ("hull", 1 );
 
# If! ARRAY
CvMemStorage * storage = cvCreateMemStorage (0 );
# Endif
Int I;
Int contour = rand () % 100 + 1;
Int hullcontour;
CvPoint pt0;
# If! ARRAY
CvSeq * ptseq = cvCreateSeq (CV_SEQ_KIND_GENERIC | CV_32SC2, sizeof (CvContour), sizeof (CvPoint), storage );
CvSeq * hull;
For (I = 0; I <contour; I ++)
{
Pt0.x = rand () % (img-> width/2) + img-> width/4;
Pt0.y = rand () % (img-> height/2) + img-> height/4;
CvSeqPush (ptseq, & pt0 );
}
Hull = cvConvexHull2 (ptseq, 0, CV_CLOCKWISE, 0 );
/* Hull = cvConvexHull2 (ptseq, 0, CV_CLOCKWISE, 1 );*/
Hullcontour = hull-> total;
# Else
CvPoint * points = (CvPoint *) malloc (contour * sizeof (points [0]);
Int * hull = (int *) malloc (contour * sizeof (hull [0]);
CvMat point_mat = cvMat (1, contour, CV_32SC2, points );
CvMat hull_mat = cvMat (1, contour, CV_32SC1, hull );
For (I = 0; I <contour; I ++)
{
Pt0.x = rand () % (img-> width/2) + img-> width/4;
Pt0.y = rand () % (img-> height/2) + img-> height/4;
Points [I] = pt0;
}
CvConvexHull2 (& point_mat, & hull_mat, CV_CLOCKWISE, 0 );
Hullcontour = hull_mat.cols;
# Endif
CvZero (img );
For (I = 0; I <contour; I ++)
{
# If! ARRAY
Pt0 = * CV_GET_SEQ_ELEM (CvPoint, ptseq, I );
/* Pt0 = ** CV_GET_SEQ_ELEM (CvPoint *, ptseq, I );*/
# Else
Pt0 = points [I];
# Endif
CvCircle (img, pt0, 2, CV_RGB (255, 0, 0), CV_FILLED );
}
# If! ARRAY
Pt0 = ** CV_GET_SEQ_ELEM (CvPoint *, hull, hullcontour-1 );
/* Pt0 = * CV_GET_SEQ_ELEM (CvPoint, hull, hullcontour-1 );*/
# Else
Pt0 = points [hull [hullcontour-1];
# Endif
 
For (I = 0; I {
# If! ARRAY
CvPoint pt = ** CV_GET_SEQ_ELEM (CvPoint *, hull, I );
/* CvPoint pt = * CV_GET_SEQ_ELEM (CvPoint, hull, I );*/
# Else
CvPoint pt = points [hull [I];
# Endif
CvLine (img, pt0, pt, CV_RGB (255, 0, 0 ));
Pt0 = pt;
}
 
CvShowImage ("hull", img );
 
CvWaitKey (0 );
 
# If! ARRAY
CvClearMemStorage (storage );
# Else
Free (points );
Free (hull );
# Endif
Return 0;
 
}


There are three comments in the Code. This is a problem I encountered when learning this program and I wrote my own test code. This code is relatively comparative.
It is easy to understand, mainly because it does not quite understand the use of the CV_GET_SEQ_ELEM macro in the program. This macro is used to extract elements from the sequence.
This program is used in three places.
Article 1:
[Cpp]
Pt0 = * CV_GET_SEQ_ELEM (CvPoint, ptseq, I );

Second:
[Cpp] ll, hullcontour-1 );

Third:
[Cpp]
CvPoint pt = ** CV_GET_SEQ_ELEM (CvPoint *, hull, I );

Obviously, the method of calling the first part is different from that of the next two parts. However, the pt0 and pt types are both CvPoint, and ptseq and hull are both CvSeq * classes.
Type, the only difference is that the first parameter in the macro, the type returned by the macro on this parameter table + *, for example: the first parameter is CvPoint, then
Return CvPoint *, and so on. In this case, both macros return a CvPoint type value. Is there any macro usage here?
Point Type in function overload! In this case, I want to call this macro in the same way, so I changed the first code
[Cpp]
Pt0 = ** CV_GET_SEQ_ELEM (CvPoint *, ptseq, I );

After the program is stopped, I changed it back here, and then changed the last two places
[Cpp]
Pt0 = * CV_GET_SEQ_ELEM (CvPoint, hull, hullcontour-1 );
 
CvPoint pt = * CV_GET_SEQ_ELEM (CvPoint, hull, I );

After running, the program is still suspended. This at least indicates that the macro call method cannot be exchanged here. But why?
Struggling for a long time, when desperate, on the Opencv Chinese Forum saw the problem about using the cvConvexHull2 function to obtain the convex hull, in
When return_points = 0, cvConvexHull2 function is used to obtain a convex shape, including a fixed point of the contour.
And when return_points is not 0, the shape point itself is obtained. The cvConvexHull2 function call code is as follows:
[Cpp]
Hull = cvConvexHull2 (ptseq, 0, CV_CLOCKWISE, 0 );

Here, the return_points is set to 0, indicating that hull does not directly point to the series of contour points, but to the pointer to the series of contour points,
This is a bit like hull is a second-level pointer! Therefore, the first parameter for macro calling in the last two places is set to CvPoint *. In this way, the system returns
CvPoint ** type. So far, this is my personal speculation and further verification is required. So I put the last parameter in the above Code
Change return_points to 1 and run. Everything is normal! Note: The macro call in the next two parts has been modified before, so you do not have to modify
. All of the above analyses and understandings are my personal opinions, not necessarily true.

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.