[图像处理]sobel算子边缘检测算法
我的程序效果:
边缘检测算法是图像处理中最为基本的问题。其目的是标志图像出亮度变化明显的点,从而反映出图像中重要变化。
先介绍一下Sobel算子:
Sobel 算子是像素图像边缘检测中最重要的算子之一,该算子包含两组3x3的,分别为横向及纵向,将之与图像作平面,即可分别得出横向及纵向的亮度近似值。如下图,Gx和Gy分别是在横向及纵向的灰度偏导的近似值。(注:对于一个彩色图要先把它转换为灰度图)
关于卷积可以看一下这个博客:https://blog..net/chaipp0607/article/details/72236892?locationNum=9&fps=1
对于每一个点我们可以获得两个方向的梯度,我们可以通过下面这个公式算出梯度的估计值。
我们定义一个阈值Gmax(这里定义Gmax = 150),如果G比Gmax大可以认为该点是一个边界值.则设置这个点为白色否则该店为黑色。这样我们就得到了通过边缘检测的图像。
代码实现:
1.彩色图转为灰度图:
QImage LeadToGrey(const QImage &source) { int w = source.width(); int h = source.height(); QImage gray(w,h,QImage::Format_RGB32); for( int i = 0; i< h; i++){ for(int j = 0; j < w; j++){ QRgb pixel = source.pixel(j,i); int grey = qGray(pixel); QRgb graypixel = qRgb(grey,grey,grey); gray.setPixel(j,i,graypixel); } } return gray; }
2.边缘检测代码:
Image LeadToEdge(QImage source) { int w = source.width(); int h = source.height(); QImage Edge(w,h,QImage::Format_RGB32); for( int i = 0; i< h; i++){ //卷积操作 for(int j = 0; j < w; j++){ double Gx = (-1)* QColor(source.pixel(getIndex(j-1,w),getIndex(i-1,h))).red() +(-2)*QColor(source.pixel(getIndex(j,w),getIndex(i-1,h))).red() +(-1)*QColor(source.pixel(getIndex(j+1,w),getIndex(i-1,h))).red() +QColor(source.pixel(getIndex(j-1,w),getIndex(i+1,h))).red() +2*QColor(source.pixel(getIndex(j,w),getIndex(i+1,h))).red() +QColor(source.pixel(getIndex(j+1,w),getIndex(i+1,h))).red(); double Gy = QColor(source.pixel(getIndex(j-1,w),getIndex(i-1,h))).red() +(2)*QColor(source.pixel(getIndex(j-1,w),getIndex(i,h))).red() +(1)*QColor(source.pixel(getIndex(j-1,w),getIndex(i+1,h))).red() +(-1)*QColor(source.pixel(getIndex(j+1,w),getIndex(i-1,h))).red() +(-2)*QColor(source.pixel(getIndex(j+1,w),getIndex(i,h))).red() +(-1)*QColor(source.pixel(getIndex(j+1,w),getIndex(i+1,h))).red(); double G = sqrt(Gx*Gx+Gy*Gy); QRgb pixel; if(G>Gmax) pixel = qRgb(255,255,255); else pixel = qRgb(0,0,0); Edge.setPixel(j,i,pixel); } } return Edge; }