In OpenCV, the speed of edge detection by using the canny operator is very fast, but it is a bit uncomfortable that the high and low thresholds need to be input. In matlab, if the threshold value is not specified, it is automatically determined by the function. Therefore, according to the practice in matlab, the system modifies the canny function so that when the user does not specify the threshold value, the threshold value is automatically determined by the function.
I added a function in the OpenCv original code library to determine the high and low thresholds.
View plaincopy to clipboardprint?
- // Follow the matlab model to automatically calculate two thresholds
- CV_IMPL void AdaptiveFindThreshold (CvMat * dx, CvMat * dy, double * low, double * high)
- {
- CvSize size;
- IplImage * imge = 0;
- Int I, j;
- CvHistogram * hist;
- Int hist_size = 255;
- Float range_0 [] = {0,256 };
- Float * ranges [] = {range_0 };
- Double PercentOfPixelsNotEdges = 0.7;
- Size = cvGetSize (dx );
- Imge = cvCreateImage (size, IPL_DEPTH_32F, 1 );
- // Calculate the edge strength and coexist in the image
- Float maxv = 0;
- For (I = 0; I <size. height; I ++)
- {
- Const short * _ dx = (short *) (dx-> data. ptr + dx-> step * I );
- Const short * _ DY = (short *) (dy-> data. PTR + dy-> step * I );
- Float * _ image = (float *) (imge-> imagedata + imge-> widthstep * I );
- For (j = 0; j <size. width; j ++)
- {
- _ Image [J] = (float) (ABS (_ DX [J]) + ABS (_ dy [J]);
- Maxv = maxv <_ image [J]? _ Image [J]: maxv;
- }
- }
- // Calculate the Histogram
- Range_0 [1] = maxv;
- Hist_size = (int) (hist_size> maxv? Maxv: hist_size );
- Hist = cvCreateHist (1, & hist_size, CV_HIST_ARRAY, ranges, 1 );
- CvCalcHist (& imge, hist, 0, NULL );
- Int total = (int) (size. height * size. width * PercentOfPixelsNotEdges );
- Float sum = 0;
- Int icount = hist-> mat. dim [0]. size;
- Float * h = (float *) cvPtr1D (hist-> bins, 0 );
- For (I = 0; I <icount; I ++)
- {
- Sum + = h [I];
- If (sum> total)
- Break;
- }
- // Calculate the high/low threshold
- * High = (I + 1) * maxv/hist_size;
- * Low = * high * 0.4;
- CvReleaseImage (& imge );
- CvReleaseHist (& hist );
- }
- Make the following changes to the cvmoderation function.
- In the function body, when the program uses two sobel operators to calculate the gradient strength in both the horizontal and vertical directions, add the following code:
- // Adaptive threshold determination
- If (low_thresh =-1 & high_thresh =-1)
- {
- AdaptiveFindThreshold (dx, dy, & low_thresh, & high_thresh );
- }
// Based on matlab, adaptive Calculation of Two thresholds <br/> CV_IMPL void AdaptiveFindThreshold (CvMat * dx, CvMat * dy, double * low, double * high) <br/>{< br/> CvSize size; <br/> IplImage * imge = 0; <br/> int I, j; <br/> CvHistogram * hist; <br/> int hist_size = 255; <br/> float range_0 [] = {0,256}; <br/> float * ranges [] = {range_0 }; <br/> double PercentOfPixelsNotEdges = 0.7; <br/> size = cvGetSize (dx); <br/> imge = cvCreateImage (size, IPL_DEPTH_32F, 1); <br/> // calculate the edge strength, coexist in the image <br/> float maxv = 0; <br/> for (I = 0; I <size. height; I ++) <br/>{< br/> const short * _ dx = (short *) (dx-> data. ptr + dx-> step * I); <br/> const short * _ dy = (short *) (dy-> data. ptr + dy-> step * I); <br/> float * _ image = (float *) (imge-> imageData + imge-> widthStep * I ); <br/> for (j = 0; j <size. width; j ++) <br/>{< br/> _ image [j] = (float) (abs (_ dx [j]) + abs (_ Dy [j]); <br/> maxv = maxv <_ image [j]? _ Image [j]: maxv; <br/>}</p> <p> // calculate the histogram <br/> range_0 [1] = maxv; <br/> hist_size = (int) (hist_size> maxv? Maxv: hist_size); <br/> hist = cvCreateHist (1, & hist_size, CV_HIST_ARRAY, ranges, 1); <br/> cvCalcHist (& imge, hist, 0, NULL); <br/> int total = (int) (size. height * size. width * PercentOfPixelsNotEdges); <br/> float sum = 0; <br/> int icount = hist-> mat. dim [0]. size; </p> <p> float * h = (float *) cvPtr1D (hist-> bins, 0); <br/> for (I = 0; I <icount; I ++) <br/>{< br/> sum + = h [I]; <br/> if (sum> total) <Br/> break; <br/>}< br/> // calculate the high/low threshold <br/> * high = (I + 1) * maxv/hist_size; <br/> * low = * high * 0.4; <br/> cvReleaseImage (& imge); <br/> cvReleaseHist (& hist ); <br/>}</p> <p> make the following changes to the cvkan function. <Br/> In the function body, when the program uses two sobel operators to calculate the gradient strength in both the horizontal and vertical directions, add the following code <br/> // adaptive threshold determination <br/> if (low_thresh =-1 & high_thresh =-1) <br/>{< br/> AdaptiveFindThreshold (dx, dy, & low_thresh, & high_thresh); <br/>}
In this way, when you specify the high/low threshold to-1 when calling the cvmoderation function, the cvmoderation function automatically determines the threshold. Finally, don't forget to recompile the cv library and update the lib and dll libraries. That's all! Http://blog.chinaunix.net/u/30231/showart_233944.html