二值图像的贴标签算法

  贴标签就是将二值图中属于同一个连通域的像素标记起来。之前编的程序需要多次遍历图像,所以速度比较慢,最近有朋友告诉我一种更简单的方法。这里对二值图中白色的连通域进行贴标签,具体步骤是:

  1、按行遍历图像,当遇到一个白点时,说明遇到了一个标签区域;

  2、将当前白点的坐标作为种子点入栈;

  3、判断栈是否为空,若栈非空,则在栈顶元素所在位置贴上对应的标签号,同时将二值图上的该位置赋成别的颜色(表明当前元素已经贴过标签),弹出栈顶元素,并将其8邻域的白点入栈,重复3直到栈空,这时,当前连通域已经完成贴标签过程;

  4、继续按行遍历图像,直到遇到下一个白点,然后重复步骤2-3,直到遍历完图像;

 1 ////////////////////////////////////////////////////
 2 //    功能:二值图贴标签(针对感兴趣区域)
 3 //    参数:
 4 //        pBin     - 二值图像
 5 //        pLabel   - 标签矩阵(在外申请,和图像同样大小,并全部置0)
 6 //        lineByte - 图像的每行字节数
 7 //        roi      - 感兴趣区域(左闭右开、上区间)
 8 //    返回值:
 9 //        nLabel   - 标签个数
10 ///////////////////////////////////////////////////
11 
12 int Labeling(unsigned char *pBin, int *pLabel, int lineByte, CRect roi)
13 {
14     //感兴趣区域的4条边界
15     int xMin = roi.left;
16     int xMax = roi.right;
17     int yMin = roi.top;
18     int yMax = roi.bottom;
19 
20     stack<CPoint> stk;
21     int i,j,x,y,k;
22     int nLabel = 0; //标签编号(从1号标签贴起,非标签区域贴0)
23     for (y=yMin; y<yMax; y++)
24     {
25         for (x=xMin; x<xMax; x++)
26         {
27             if (pBin[y*lineByte+x]==255) //以找到的第一个白点为种子点
28             {
29                 nLabel++;
30                 stk.push(CPoint(x,y));   //将种子点入栈
31                 pLabel[y*lineByte+x] = nLabel;
32                 pBin[y*lineByte+x] = nLabel*40;    
33 
34                 //若栈非空,弹出一个元素,并将其8邻域内的白点入栈,栈空时当前连通域完成贴标签
35                 while (!stk.empty())     
36                 {
37                     CPoint pt = stk.top();
38                     stk.pop();
39                     i = pt.y;
40                     j = pt.x;
41                     k = i*lineByte+j;    
42                     if (i>yMin && j>xMin && pBin[k-lineByte-1]==255) //左上
43                     {
44                         stk.push(CPoint(j-1,i-1));
45                         pLabel[k-lineByte-1] = nLabel;
46                         pBin[k-lineByte-1] = nLabel*40;
47                     }
48                     if (i>yMin && pBin[k-lineByte]==255) //
49                     {
50                         stk.push(CPoint(j,i-1));
51                         pLabel[k-lineByte] = nLabel;
52                         pBin[k-lineByte] = nLabel*40;
53                     }
54                     if (i>yMin && j<xMax-1 && pBin[k-lineByte+1]==255) //右上
55                     {
56                         stk.push(CPoint(j+1,i-1));
57                         pLabel[k-lineByte+1] = nLabel;
58                         pBin[k-lineByte+1] = nLabel*40;
59                     }
60                     if (j>xMin && pBin[k-1]==255) //
61                     {
62                         stk.push(CPoint(j-1,i));
63                         pLabel[k-1] = nLabel;
64                         pBin[k-1] = nLabel*40;
65                     }
66                     if (j<xMax-1 && pBin[k+1]==255) //
67                     {
68                         stk.push(CPoint(j+1,i));
69                         pLabel[k+1] = nLabel;
70                         pBin[k+1] = nLabel*40;
71                     }
72                     if (i<yMax-1 && j>xMin && pBin[k+lineByte-1]==255) //左下
73                     {
74                         stk.push(CPoint(j-1,i+1));
75                         pLabel[k+lineByte-1] = nLabel;
76                         pBin[k+lineByte-1] = nLabel*40;
77                     }
78                     if (i<yMax-1 && pBin[k+lineByte]==255) //
79                     {
80                         stk.push(CPoint(j,i+1));
81                         pLabel[k+lineByte] = nLabel;
82                         pBin[k+lineByte] = nLabel*40;
83                     }
84                     if (i<yMax-1 && j<xMax-1 && pBin[k+lineByte+1]==255) //右下
85                     {
86                         stk.push(CPoint(j+1,i+1));
87                         pLabel[k+lineByte+1] = nLabel;
88                         pBin[k+lineByte+1] = nLabel*40;
89                     }
90                 }
91             }
92         }
93     }
94 
95     return nLabel;
96 }

 

posted on 2013-01-25 16:54  文森vincent  阅读(2986)  评论(0编辑  收藏  举报

导航