/************************************************************************* * * \函数名称: * Canny() * * \输入参数: * unsigned char *pUnchImage- 图象数据 * int nWidth - 图象数据宽度 * int nHeight - 图象数据高度 * double sigma - 高斯滤波的标准方差 * double dRatioLow - 低阈值和高阈值之间的比例 * double dRatioHigh - 高阈值占图象象素总数的比例 * unsigned char *pUnchEdge - canny算子计算后的分割图 * * \返回值: * 无 * * \说明: * canny分割算子,计算的结果保存在pUnchEdge中,逻辑1(255)表示该点为 * 边界点,逻辑0(0)表示该点为非边界点。该函数的参数sigma,dRatioLow * dRatioHigh,是需要指定的。这些参数会影响分割后边界点数目的多少 ************************************************************************* */ void Canny(unsigned char *pUnchImage, int nWidth, int nHeight, double sigma, double dRatioLow, double dRatioHigh, unsigned char *pUnchEdge) { // 经过高斯滤波后的图象数据 unsigned char * pUnchSmooth ; // 指向x方向导数的指针 int * pnGradX ; // 指向y方向导数的指针 int * pnGradY ; // 梯度的幅度 int * pnGradMag ; pUnchSmooth = new unsigned char[nWidth*nHeight] ; pnGradX = new int [nWidth*nHeight] ; pnGradY = new int [nWidth*nHeight] ; pnGradMag = new int [nWidth*nHeight] ; // 对原图象进行滤波 GaussianSmooth(pUnchImage, nWidth, nHeight, sigma, pUnchSmooth) ; // 计算方向导数 DirGrad(pUnchSmooth, nWidth, nHeight, pnGradX, pnGradY) ; // 计算梯度的幅度 GradMagnitude(pnGradX, pnGradY, nWidth, nHeight, pnGradMag) ; // 应用non-maximum 抑制 NonmaxSuppress(pnGradMag, pnGradX, pnGradY, nWidth, nHeight, pUnchEdge) ; // 应用Hysteresis,找到所有的边界 Hysteresis(pnGradMag, nWidth, nHeight, dRatioLow, dRatioHigh, pUnchEdge); // 释放内存 delete pnGradX ; pnGradX = NULL ; delete pnGradY ; pnGradY = NULL ; delete pnGradMag ; pnGradMag = NULL ; delete pUnchSmooth ; pUnchSmooth = NULL ; }
// Canny算子 void Canny(LPBYTE pGray, SIZE sz, double sigma, double dRatLow, double dRatHigh, LPBYTE pResult) { //经过高斯滤波后的图像 LPBYTE pGaussSmooth; pGaussSmooth = new unsigned char[sz.cx*sz.cy]; //x方向导数的指针 int *pGradX; pGradX = new int[sz.cx*sz.cy]; //y方向 int *pGradY; pGradY = new int[sz.cx*sz.cy]; //梯度的幅度 int *pGradMag; pGradMag = new int[sz.cx*sz.cy]; //对原图高斯滤波 GaussianSmooth(sz,pGray,pGaussSmooth,sigma); //计算方向导数和梯度的幅度 Grad(sz,pGaussSmooth,pGradX,pGradY,pGradMag); //应用非最大抑制 NonmaxSuppress(pGradMag,pGradX,pGradY,sz,pResult); //应用Hysteresis,找到所有边界 Hysteresis(pGradMag,sz,dRatLow,dRatHigh,pResult); delete[] pGradX; pGradX = NULL; delete[] pGradY; pGradY = NULL; delete[] pGradMag; pGradMag = NULL; delete[] pGaussSmooth; pGaussSmooth = NULL; }