/*ConnectivityMark参数说明:区域标记
ConnectivityMark(
Uchar* ioput, 输入二值图像/输出连通标记图像
int connectType, 连通域类型,只能是:4 or 8(背景标记用4连通,目标标记用8连通)
int* connectArea, 连通区域面积统计(数组大小等于图像)
int* areaNumber, 连通区数量
int rowSize, 图像行数
int colSize, 图像列数
Uchar backFlag, 背景标签
Uchar targetFlag 目标标签
)
*/
static int ConnectivityMark(Uchar* ioput, int connectType, int* connectArea, int* areaNumber, int rowSize, int colSize, Uchar backFlag, Uchar targetFlag)
{
//connectType=4、8
int Neighbor[2][8] = {};
int coordinateNum = connectType;
if (connectType==4)
{
int Neighbor4[2][4] =
{
{ -1, 0, 1, 0 },
{ 0, 1, 0, -1 }
};
for (int i = 0; i < 2; i++)
{
for (int j = 0; j < 4; j++)
{
Neighbor[i][j] = Neighbor4[i][j];
}
}
}
else if (connectType == 8)
{
int Neighbor8[2][8] =
{
{ -1, -1, -1, 0, 0, 1, 1, 1 },
{ -1, 0, 1, -1, 1, -1, 0, 1 }
};
for (int i = 0; i < 2; i++)
{
for (int j = 0; j < 8; j++)
{
Neighbor[i][j] = Neighbor8[i][j];
}
}
}
else
{
printf(" Error in ConnectivityMark : connectType is not 4 or 8");
return -1;
}
int maxSize = rowSize * colSize;
int* Q = (int*)malloc(2 * maxSize * sizeof(int));//maxSize * 2数组
memset(Q, 0, 2 * maxSize * sizeof(int));
int front = 0;//指明队头的位置
int rear = 0; //指明队尾的下一个位置;front = rear表示队空
Uchar flag = 0; //连通区标号
int wide = OFF_BORDER_WIDTH;
for (int i = wide; i < rowSize - wide; i++)
{
for (int j = wide; j < colSize - wide; j++)
{
if (ioput[i * colSize + j] == targetFlag)
{
if (front == rear)
{
flag = flag + 1;
flag = minf(flag, MAXIMUM_PIXEL_VALUE);//不超过255
}
ioput[i * colSize + j] = flag;//给白色像素赋值为连通区域标号
Q[rear * 2] = i;
Q[rear * 2 + 1] = j;
rear = rear + 1; //队尾后移
while (front != rear)
{
//队头出队
int temp_i = Q[front * 2];
int temp_j = Q[front * 2 + 1];
front = front + 1;
//把队头位置像素点8连通邻域中未作标记的白色像素点入队
for (int k = 0; k < coordinateNum; k++)
{
int y = temp_i + Neighbor[0][k];
int x = temp_j + Neighbor[1][k];
if ((y >= 0) & (y < rowSize) & (x >= 0) & (x < colSize))
{
if (ioput[y * colSize + x] == targetFlag)
{
ioput[y * colSize + x] = flag;
Q[rear * 2] = y;
Q[rear * 2 + 1] = x;
rear = rear + 1;
}
}
}
}
}
}
}
*areaNumber = flag;
for (int i = wide; i < rowSize - wide; i++)
{
for (int j = wide; j < colSize - wide; j++)
{
if (ioput[i * colSize + j] != backFlag)
{
connectArea[ioput[i * colSize + j]] = connectArea[ioput[i * colSize + j]] + 1;
}
}
}
free(Q);
Q = NULL;
return 0;
}
区域标记
猜你喜欢
转载自blog.csdn.net/u013297911/article/details/88057955
今日推荐
周排行