赞
踩
a. 分别使用 x , y x,y x,y两个方向的卷积核进行处理:
b. 计算梯度 G G G 和方向 θ \theta θ:
把 θ \theta θ 近似到四个方向,分别代表水平,垂直和两个对角线方向(0°,45°,90°,135°)
非极大值抑制是一种边缘稀疏技术,通常得出来的梯度边缘不止一个像素宽,而是多个像素宽。非最大值抑制能帮助保留局部最大梯度而抑制所有其他梯度值。这意味着只保留了梯度变化中最大的位置,其他都为0。算法如下:
a. 将当前的梯度与正负梯度方向的两个像素的梯度G1、G2进行比较
b. 如果当前像素的梯度强度与另外两个像素相比最大,则该像素点保留为边缘点,否则该像素点将被抑制;比如当前点的梯度方向指向正上方90°方向,那它需要和垂直方向的正上方和正下方的像素的梯度进行比较。
伪代码:
if G>G1 && G>G2
G may be edge
else
G should be suppressed
if G>HighThreshold
G is a strong edge
else if G>= LowThreshold
G is a weak edge
else
G should be suppressed
伪代码:
if G is weak edge && connected to strong edge
G is a real edge
else
G should be suppressed
#include <opencv2/opencv.hpp> #include <iostream> using namespace cv; using namespace std; Mat src,src_gray; Mat dst,detected_edges; int lowThreshold = 0; const int kernel_size = 3; const int max_lowThreshold = 100; const char* window_name = "Canny detectes edges"; static void CannyThreshold(int, void*) { blur(src_gray,detected_edges,Size(3,3)); Canny(detected_edges,detected_edges,lowThreshold,lowThreshold*3,kernel_size); //高阈值是低阈值的3倍 dst = Scalar::all(0); src.copyTo(dst,detected_edges); //detected_edges是Canny算子检测的结果,作为mask,将src复制给dst imshow(window_name,dst); } int main(void) { src = imread("../res/lena.jpeg",cv::IMREAD_COLOR); if(src.empty()) { cout << "can't load image" << endl; } dst.create(src.size(),src.type()); cv::cvtColor(src,src_gray,cv::COLOR_BGR2GRAY); namedWindow(window_name, cv::WINDOW_AUTOSIZE); createTrackbar("Min Threshold",window_name,&lowThreshold,max_lowThreshold,CannyThreshold); CannyThreshold(0,0); waitKey(0); return 0; }
结果:
void cv::Canny
(
InputArray image, // 8-bit input image
OutputArray edges, // 输出edge图,和输入一样,单通道 8bits 图
double threshold1, // lowThreshold
double threshold2, // highThreshold
int apertureSize = 3, // 定义调用Sobel核大小
bool L2gradient = false // 计算梯度方式,
L
2
L_2
L2是精确的,
L
1
L_1
L1是近似
)
输入的是:分别对图像x ,y 的导数的结果
void cv::Canny
(
InputArray dx, // 16-bit x derivative of input image (CV_16SC1 or CV_16SC3).
InputArray dy, // 16-bit y derivative of input image (same type as dx).
OutputArray edges, // single channels 8-bit image, which has the same size as input .
double threshold1, // lowThreshold
double threshold2, // highThreshold
bool L2gradient = false // 和上面一样
)
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。