繁体   English   中英

Matlab找到几个像素的聚类中心并计算聚类

[英]Matlab finding the center of cluster of a few pixels and counting the clusters

所以我有一个由1和0组成的矩阵A,我有大约10到14个许多像素的白点,但是我只希望每个白色簇的1个白色像素/中心坐标,如何计算多少个簇有他们的中心。

试想一下矩阵A,白色的夜空从黑色的天空开始,我如何计算星星和星星的中心,再加上星星是由白色像素簇组成的。

集群的大小也不尽相同。

这是一些使用bwlabel和/或regioprops的代码,分别用于识别矩阵中的连接组件和其他一些属性。 我认为这非常适合您的问题; 但是,您可能希望稍微修改一下我的代码,将其作为起点。

clear
clc

%// Create dummy matrix.
BW = logical ([ 1     1     1     0     1     1     1     0
                1     1     1     0     1     1     1     0
                1     1     1     0     1     1     1     0
                0     0     0     0     0     0     0     0
                0     0     0     0     0     1     1     0
                1     1     1     1     0     1     1     0
                1     1     1     1     0     1     1     0
                1     1     1     1     0     0     0     0]);

%// Identify clusters.
L = bwlabel(BW,4)

矩阵L看起来像这样:

L =

     1     1     1     0     3     3     3     0
     1     1     1     0     3     3     3     0
     1     1     1     0     3     3     3     0
     0     0     0     0     0     0     0     0
     0     0     0     0     0     4     4     0
     2     2     2     2     0     4     4     0
     2     2     2     2     0     4     4     0
     2     2     2     2     0     0     0     0

在这里,您可以通过多种方法来定位群集的中心。 第一个使用bwlabel的输出查找每个簇并在循环中计算坐标。 它可以正常工作,但它的教学方法有点长,而且效率不高。 @nkjt提到的第二种方法使用regionprops,它使用'Centroid'属性来实现您想要的功能。 所以这是两种方法:

方法1 :有点复杂,所以bwlabel识别了4个簇,这很有意义。 现在,我们需要确定每个集群的中心。 我的方法可能会简化; 但是我有点没时间了,所以可以随意修改它。

%// Get number of clusters
NumClusters = numel(unique(L)) -1;

Centers = zeros(NumClusters,2);
CenterLinIdices = zeros(NumClusters,1);

for k = 1:NumClusters

%// Find indices for elements forming each cluster.
    [r, c] = find(L==k);

%// Sort the elements to know hot many rows and columns the cluster is spanning.
    [~,y] = sort(r);
    c = c(y);
    r = r(y);

    NumRow = numel(unique(r));
    NumCol = numel(unique(c));

%// Calculate the approximate center of the cluster.
    CenterCoord = [r(1)+floor(NumRow/2) c(1)+floor(NumCol/2)];

%// Actually this array is not used here but you might want to keep it for future reference.
    Centers(k,:) = [CenterCoord(1) CenterCoord(2)];

%// Convert the subscripts indices to linear indices for easy reference.
    CenterLinIdices(k) = sub2ind(size(BW),CenterCoord(1),CenterCoord(2));
end

%// Create output matrix full of 0s, except at the center of the clusters.
BW2 = false(size(BW));
BW2(CenterLinIdices) = 1

BW2 =

     0     0     0     0     0     0     0     0
     0     1     0     0     0     1     0     0
     0     0     0     0     0     0     0     0
     0     0     0     0     0     0     0     0
     0     0     0     0     0     0     0     0
     0     0     0     0     0     0     1     0
     0     0     1     0     0     0     0     0
     0     0     0     0     0     0     0     0

方法2使用regionprops和'Centroid'属性。

有了矩阵L后,应用regionprops并将输出连接起来以获得直接包含坐标的数组。 简单得多!

%// Create dummy matrix.
BW = logical ([ 1     1     1     0     1     1     1     0
                1     1     1     0     1     1     1     0
                1     1     1     0     1     1     1     0
                0     0     0     0     0     0     0     0
                0     0     0     0     0     1     1     0
                1     1     1     1     0     1     1     0
                1     1     1     1     0     1     1     0
                1     1     1     1     0     0     0     0]);

%// Identify clusters.
L = bwlabel(BW,4)

s = regionprops(L,'Centroid');

CentroidCoord = vertcat(s.Centroid)

这给出了:

CentroidCoord =

    2.0000    2.0000
    2.5000    7.0000
    6.0000    2.0000
    6.5000    6.0000

使用地坪时,这要简单得多,并提供相同的输出。

希望有帮助!

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM