机器视觉入门之路(四十,霍夫变换(hough transform)图像(改进),c++)

名家的图像处理(左飞)把你引到道上,你却要找人家的错误,真不知天高地厚,还好,在科学的世界里,更纯粹吧!

虽然歪打正着,花了很大功夫把他画出来,导致画线函数自己现在看上去,怪怪的,那么,就下功夫改进吧!因为在自己家里改,别人也不知道,就这样吧,走起!

看到这个公式了吧!红色的!

void HoughLine(BYTE* image0, BYTE* &image1, unsigned int &w, unsigned int &h,int type) 

.......//type==1,使用梯度图像

 for(i=0; i<360; i++)
            {
                if( tempImage[(y*w+x)] >this->m_grayThres)//
                {
                    tp = (int)( x*sinValue[i] + y*cosValue[i]);
                    if (tp<0||HoughBuf[tp][i]==255) continue;
                    HoughBuf[tp][i] += scale;
                }
            }

改正为:  tp = (int)( x*cosValue[i]+ y*sinValue[i] );名家的东西,真是慎之又慎!不敢冒犯啊!哈哈!心口不实!

好,我们的霍夫直线画线函数也跟着改了,真是舒服多了!

void HoughShow(BYTE* image0, BYTE* image1, unsigned int &w, unsigned int &h,int K,int type)
{
    BYTE* houghImage=NULL;
    
    unsigned int hw=w,hh=h;
    HoughLine(image0,houghImage,hw,hh,type);

    memcpy(image1,image0,w*h*4);
    BYTE** imageBuf1 = CreatImage(image1,w,h);
    //将图像由线序列转换为矩阵形式
    BYTE** houghBuf = CreatImage(houghImage,hw,hh);
    int x,y,a;
  
    //依次对Hough图像的每个像素进行检测
    for(y=0; y<hh; y++)
    {
        for(x=0; x<hw; x++)
        {         
            if(houghBuf[y][x*4]>K)//x/*=a*/,y/*=p*/
            {
                //DrawLine(imageBuf1,w,h,x/*=\Theta*/,y/*=p*/);//202007030827
                DrawLineimprove2(imageBuf1, w, h, x/*=\Theta*/, y/*=p*/);//202007030925
            }
        }
    }
    free(houghImage);
    free(houghBuf);
    free(imageBuf1);
}

 void DrawLineimprove2(BYTE** imageBuf, int w, int h, int a, int p)//202007030925
{
    double k, b;
    int x, y;
    k = -cos(a*3.1415926535 / 180) / sin(a*3.1415926535 / 180);
    
    if (abs(k)>65635)    //=90,认为无穷大接近pi/2或-pi/2
    {
        //计算直线方程的参数         
        for (y = 0; y<h - 2; y++)
        {
            if (p >= 0 && p<w - 2)
            {
                imageBuf[y][p * 4] =/*255*/0;
                imageBuf[y][p * 4 + 1] = 0;
                imageBuf[y][p * 4 + 2] = 250;
                imageBuf[y][p * 4 + 3] = 255;
            }
        }
    }
    else
    {
        b = p / sin(a*3.1415926535 / 180);    
        k = -cos(a*3.1415926535 / 180) / sin(a*3.1415926535 / 180);

        y = 0;
        x = 0;
        //斜率小于1的情况
        if (abs(k) <= 1)
        {
            for (x = 0; x<w - 2; x++)
            {
                y = (int)(k*x + b);
                if (y >= 0 && y<h - 2)
                {
                
                    imageBuf[y][x * 4] =0;
                    imageBuf[y][x * 4 + 1] = 0;
                    imageBuf[y][x * 4 + 2] = 250;
                    imageBuf[y][x * 4 + 3] = 255;
                    
                }
            }
        }
        //斜率大于1的情况
        else
        {
            for (y = 0; y<h - 2; y++)
            {
                x = (int)(y / k - b / k);
                if (x >= 0 && x<w - 2)
                {
                    imageBuf[y][x * 4] =0;
                    imageBuf[y][x * 4 + 1] = 0;
                    imageBuf[y][x * 4 + 2] = 250;
                    imageBuf[y][x * 4 + 3] = 255;
                }
            }
        }
    }
}

BYTE** CreatImage(BYTE* image, unsigned int width, unsigned int height, int bt=4)
{
    BYTE** imageBuf = (BYTE**)malloc(sizeof(BYTE*)*(height));
    for(int y=0; y<height; y++)
    {
        //使imageBuf中每个指针分别指向其下标表示的行的行首地址
        imageBuf[y] = image+y*width*bt; 
    }
    return imageBuf;
}

好,我们看效果,好像也没什么改变嘛!别人不知道,自己还不知道吗?再也不用惦记了,放下了!