opencv kmeans聚类错误的输出

时间:2012-06-29 08:06:52

标签: opencv k-means

我正在尝试在openCV中的图像上实现kmeans聚类(使用C)。输出非常奇怪,而不是产生一些颜色层的聚集图像。我也尝试调试代码,但无法理解它可能出错的地方。

这是输入和输出图像。

enter image description here

右边是输出,左边是输入图像。

以下是代码:

image = cvLoadImage( "pic65.png", CV_LOAD_IMAGE_UNCHANGED);
sample = cvCreateMat( image->height*image->width, 5, CV_32FC1 );
clusters = cvCreateMat( image->height*image->width, 1, CV_32SC1 );

data = (uchar *)image->imageData;
for(i=0;i<image->height;i++)
{
                            for(j=0;j<image->width;j++)
                            {
                            cvSetReal2D( sample, k, 0, i);
                            cvSetReal2D( sample, k, 1, j);
                            b = data[i*image->widthStep + j*image->nChannels +0];
                            g = data[i*image->widthStep + j*image->nChannels +1];
                            r = data[i*image->widthStep + j*image->nChannels +2];
                            cvSetReal2D( sample, k, 2, b);
                            cvSetReal2D( sample, k, 3, g);
                            cvSetReal2D( sample, k, 4, r);
                            k++;
                            }
}
count = get_clusters();

cvKMeans2(sample,count,clusters,cvTermCriteria(CV_TERMCRIT_EPS+CV_TERMCRIT_ITER,100,0 ));

for (x = 0; x < image->height; x++)
{
for (y = 0; y < image->width; y++)
{
    index = x * image->width + y;
    cluster_index = cvGetReal2D(clusters,index,0);
    data[x*image->widthStep + y*image->nChannels +0] = cl[cluster_index][0];
    data[x*image->widthStep + y*image->nChannels +1] = cl[cluster_index][2];
    data[x*image->widthStep + y*image->nChannels +2] = cl[cluster_index][2];
}
}

get_clusters方法根据阈值在这种情况下返回输入图像中的颜色簇数。如果需要,我也可以为你提供get_clusters的代码,但我认为它是正确的。

有人可以指出哪里出错了。任何形式的帮助表示赞赏。 提前谢谢。

编辑:我想要的输出如下:

enter image description here

1 个答案:

答案 0 :(得分:1)

判断您的“所需输出”图像时,您对kmeans的使用是错误的。像素坐标应该在聚类中不起作用。你应该只将颜色三元组交给kmeans。

sample = cvCreateMat( image->height*image->width, 3, CV_32FC1 );

...

                  for(j=0;j<image->width;j++)
                      {
                        b = data[i*image->widthStep + j*image->nChannels +0];
                        g = data[i*image->widthStep + j*image->nChannels +1];
                        r = data[i*image->widthStep + j*image->nChannels +2];
                        cvSetReal2D( sample, k, 0, b);
                        cvSetReal2D( sample, k, 1, g);
                        cvSetReal2D( sample, k, 2, r);
                        k++;
                      }

然后,在设置数据时,您还会有一个索引错误。