Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>The problem you are describing is generally referred to as <a href="http://en.wikipedia.org/wiki/Cluster_analysis" rel="nofollow noreferrer">clustering or cluster analysis</a>. Its can be quite difficult depending on your data set and your analysis constraints. However, in your case it is simple because you have a hard threshold (5 pixels) to use.</p> <p>Aardvarkk has already put out a great solution but it doesn't really demonstrate the process of clustering. Here is a very simple way you could cluster your data and get more or less the same result.</p> <ol> <li>Compute the pairwise distance between your points. For N points this results in an NxN matrix</li> <li>Threshold that matrix</li> <li>Iterate through the rows of the matrix</li> </ol> <p>Each iteration would look like the following:</p> <ul> <li>if <code>i</code> is already clustered, continue</li> <li>if <code>i</code> isn't in a cluster, create a new cluster and assign <code>i</code> to it</li> <li>find all other points that are close to <code>i</code> (columns in row <code>i</code> that are equal to 1)</li> <li>Check to see if any of those points are already in a cluster</li> <li>If yes set <code>i</code> and all points close to <code>i</code> to the minimum cluster id </li> <li>If no set <code>i</code> and all points close to <code>i</code> to <code>i's</code> cluster</li> </ul> <p>Here is a quick example I whipped up:</p> <pre><code>%Generate random points nPts = 300; clustId = zeros(nPts,1); clusterCount = 0; x = randi(3, [1, nPts])*10+ randn(1, nPts); y = randi(3, [1, nPts])*10 + randn(1, nPts); %Compute the distance matrix from http://goo.gl/8mAoC dist = distance([x;y], [x;y]); maxDist = 5; binDist = dist &lt;= maxDist; for i = 1:nPts % if this point is already clustered skip it if clustId(i) ~= 0 continue; end %if the current point isn't in a cluster, create a new cluster and add %the point to that cluster if clustId(i) == 0 clusterCount = clusterCount+1; clustId(i) = clusterCount; fprintf('New point, creating cluster:%d\n', clusterCount); end % get the indices of the points that collide with the i idx = binDist(:,i); % check to see if idx contains points that already belong to another clustered % if it doesn't collisionIdx will be equal to i collisionIdx = idx &amp; clustId&gt;0; %get the smallest cluster from collisionIdx mergeClustId = min(clustId(collisionIdx)); %assing all the original points to that cluster clustId(idx) = mergeClustId; end </code></pre> <p>Simply iterate through the cluster Ids to calculate the centroids:</p> <pre><code>cx = []; cy = []; for i = 1:clusterCount idx = clustId == i; cx(i) = mean(x(idx)); cy(i) = mean(y(idx)); end </code></pre> <p>Then plot the results with: </p> <pre><code>figure; plot(cx,cy,'c.', 'markersize', 50); hold on; plot(x,y,'.'); </code></pre> <p><img src="https://i.stack.imgur.com/jUGTV.png" alt="enter image description here"></p>
    singulars
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. VO
      singulars
      1. This table or related slice is empty.
    2. VO
      singulars
      1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload