【问题标题】:Finding regions in scattered data在分散的数据中寻找区域
【发布时间】:2013-06-17 13:21:51
【问题描述】:

我在 Nx3 矩阵中有许多分散的数据集,用scatter3 绘制的一个简单示例如下所示(pastebin of the raw values): 我的每个数据集都有任意数量的区域/斑点;例如上面的例子有 4 个。

有人知道以编程方式查找这种数据形式的区域数量的简单方法吗?

我最初的想法是使用delaunayTriangulationconvexHull 的方法,但是如果没有任何数据处理,这仍然只能找到整个地块的外部体积,而不是每个区域。

我的下一个想法将涉及获取每个点的最近邻统计信息,询问它是否在另一个点的网格大小距离内,然后将那些在单独的 blob/clusters 集中在一起。

是否有我不知道的更高级别的 Matlab 函数可以帮助我,或者有没有人有更好的建议如何从这样的数据中提取区域计数?

【问题讨论】:

    标签: algorithm matlab


    【解决方案1】:

    听起来您需要一个聚类算法。幸运的是,MATLAB 提供了许多开箱即用的方法。有很多算法可供选择,听起来您需要事先不知道集群数量的东西,对吗?

    如果是这种情况,并且您的数据与您的示例一样“好”,我建议 kmeans 结合正确选择“k”的技术,如 here 建议的那样。

    当然还有其他选项,我建议您了解更多关于 MATLAB 中的聚类选项的信息,这里有一个不错的 reference 以供阅读。

    【讨论】:

    • 谢谢!好的建议。我会看看,看看这是怎么回事。很快就会回来报告。
    • kmeans 引起了一些问题,但是您的链接对我有很大帮助。我有一个使用距离作为标准的分层聚类的工作解决方案;按照您的第三个链接。非常感谢。
    【解决方案2】:

    确定数据集中不同集群的数量是一个棘手的问题,而且可能比我们乍看之下想的要难。事实上,像 k-means 这样的算法在很大程度上依赖于此。 Wikipedia 上面有一篇不错的文章,但是没有明确简单的方法。

    那里提到的Elbow 方法似乎比较容易做到,尽管计算成本可能很高。本质上,您可以尝试使用不同数量的聚类,并选择所解释的方差增长不大且趋于平稳的数量。

    此外,簇的概念需要明确定义 - 如果放大任何斑点会显示与图片中的角结构相似的结构怎么办?

    【讨论】:

    • 谢谢,我会通读一遍。在回答您的第二个问题时:该问题将受到我数据的网格大小的限制,因此在这些范围内不会有任何可见的子结构。
    • 实际上,我误读了您关于您的问题的意思。有效点,尽管我对我的数据了解得足够多,知道在这种特殊情况下这不会成为问题;但肯定要考虑一般情况。
    【解决方案3】:

    我建议实施高斯混合模型的“轻量级”版本。 让每个点为一个立方体“投票”。在上面的例子中,所有点都以 (-1.5,-1.5,0) 为中心 每个都会在正方形 [-1,-2]x[-1,-2]x[0.2,-0.2] 上加一个 +1。最后,您可以分析投票矩阵中的峰值。

    【讨论】:

      【解决方案4】:

      为了完整性,这个问题的答案(我已经建立)比分层聚类要简单得多;这可以提供更好的结果,并且可以区分 1 个集群或 2 个集群(我无法通过 MarkV 的建议解决这个问题)。这假设您的数据位于已知大小的常规网格上,并且您有未知数量的簇,这些簇至少相隔 2*(网格大小):

      % Idea is as follows: 
      % * We have a known grid size, dx. 
      % * A random point [may as well be minima(1,:)] will be in a cluster of 
      %   values if any others in the list lie dx away (with one dimention 
      %   varied), sqrt(2)*dx (two dimensions varied) or sqrt(3)*dx (three 
      %   dimensions varied).
      % * Chain these objects together until all are found, any with distances
      %   beyond sqrt(3)*dx of the cluster are ignored for now.
      % * Set this cluster aside, repeat until no minima data is left.
      
      function [blobs, clusterIdx] = findClusters(minima,dx)
      %problem setup
      dx2 = sqrt(2)*dx;
      dx3 = sqrt(3)*dx;
      eqf = @(list,dx,dx2,dx3)(abs(list-dx) < 0.001 | abs(list-dx2) < 0.001 | abs(list-dx3) < 0.001);
      notDoneClust = true;
      notDoneMinima = true;
      
      clusterIdx = zeros(size(minima,1),1);
      point = minima(1,:);
      list = minima(2:end,:);
      blobs = 0;
      
      while notDoneMinima
          cluster = nan(1,3);
      
          while notDoneClust
              [~, dist] = knnsearch(point,list); %All distances to each other point in data
              nnidx = eqf(dist,dx,dx2,dx3); %finds indexes of nn values to point
      
              cluster = cat(1,cluster,point,list(nnidx,:)); %add points to current cluster
              point = list(nnidx,:); %points to check are now all values that are nn to initial point
              list = list(~nnidx,:); %list is now all other values that are not in that list
      
              notDoneClust = ~isempty(point); %if there are no more points to check, all values of the cluster have been found
          end
          blobs = blobs+1;
          clusterIdx(ismemberf(minima,cluster(2:end,:),'rows')) = blobs;
      
          %reset points and list for a new cluster
          if ~isempty(list)
              if length(list)>1
                  point = list(1,:);
                  list = list(2:end,:);
                  notDoneClust = true;
              else
                  %point is a cluster of its own. Don't reset loops, add point in
                  %as a cluster and exit (NOTE: I have yet to test this portion).
                  blobs = blobs+1;
                  clusterIdx(ismemberf(minima,point,'rows')) = blobs;
                  notDoneMinima = false;
              end
          else
              notDoneMinima = false;
          end
      end
      end
      

      我完全理解这种方法对于一般意义上的数据聚类是没有用的,因为任何离群的数据都会被标记为一个单独的聚类。这(如果发生)是我无论如何都需要的,所以这可能只是一个边缘情况。

      【讨论】:

        猜你喜欢
        • 2017-07-23
        • 1970-01-01
        • 2014-02-25
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多