本文主要介绍:利用递归函数,求四连通和八连通邻域。
一、变量定义
1.定义邻域类型
int m_linkType = 4 // 4表示4连通邻域 8表示8连通邻域
POINT posDir[8]; posDir[0].x=0; posDir[0].y = -1; //上 posDir[1].x=0; posDir[1].y=1; //下 posDir[2].x=-1; posDir[2].y=0; //左 posDir[3].x=1;posDir[3].y=0; //右 posDir[4].x=-1; posDir[4].y=-1; //左上 posDir[5].x=1;posDir[5].y=-1; //右上 posDir[6].x=-1;posDir[6].y=1; //左下 posDir[7].x=1;posDir[7].y=1; //右下
/****************************************************************** 功能:对某个像素点,用递归函数求连通域 参数: Inimg :输入图像矩阵 Flag :像素点有没有遍历过标志 0 表示没有 非0表示有 如果对连通域编号,可以赋值为编号值 row :像素点行 col :像素点列 Width :图像矩阵宽 Height:图像矩阵行 Value :起始点像素值 ******************************************************************/ void ConnectRegion(unsigned char *Inimg,unsigned char *Flag,int row, int col,int Width,int Height,int Value) { if(row<0||row>=Height||col<0||col>=Width) //如果该次遍历点的行列数,超出图像大小, return; //则结束本次调用 int tIND2 = row*Width+col; if(Inimg[tIND2]!=Value||Flag[tIND2]!=0) //如果该次遍历点的像素值不等于起始像素点值, return; //或该点已遍历过,则结束本次调用 Flag[tIND2] =1;//标记该点已遍历过,也可以赋值为联通域编号,非0即可 //这里,可以得到与起始点连通的点的行列号 row col //可以根据需求,对行列号存储或计算连通域边界 if(m_linkType==4) for(int i=0;i<4;i++)//递归搜寻连通域 ConnectRegion(Inimg,Flag,row+posDir[i].y,col+posDir[i].x,Width,Height,Value); if(m_linkType==8) for(int i=0;i<8;i++)//递归搜寻连通域 ConnectRegion(Inimg,Flag,row+posDir[i].y,col+posDir[i].x,Width,Height,Value); }
3.调用形式
//假定图像矩阵Inimg已知 Width:图像宽 Height:图像高 unsigned char *Flag = new unsigned char[Width*Height];//初始化遍历标志 ZeroMemory(Flag,sizeof(unsigned char)*Width*Height); int tIND1,tIND2; for(int i=0; i<Height; i++) { tIND1 = i*Width; for(int j=0;j<Width;j++) { tIND2 = tIND1 + j; if(Flag[tIND2]==0)//该点没有遍历过,即没有连通号 ConnectRegion(Inimg,Flag,i,j,Width,Height,Inimg[tIND2]);//寻找与该点连通的区域 } }