0
$\begingroup$

I have the following piece of code:

function label = kmeans(X, k)
% Perform k-means clustering.
%   X: d x n data matrix
%   k: number of seeds
% Written by Michael Chen (sth4nth@gmail.com).
n = size(X,2);
last = 0;
label = ceil(k*rand(1,n));  % random initialization
while any(label ~= last)
    [u,~,label] = unique(label);   % remove empty clusters
    k = length(u);
    E = sparse(1:n,label,1,n,k,n);  % transform label into indicator matrix
    m = X*(E*spdiags(1./sum(E,1)',0,k,k));    % compute m of each cluster
    last = label;
    [~,label] = max(bsxfun(@minus,m'*X,dot(m,m,1)'/2),[],1); % assign samples to the nearest centers
end
[~,~,label] = unique(label);

I would like to convert it to Mathematica, but I am not sure how to handle the matrix operations such as spdiags annd bsxfun in Mathematica...

For the moment, I have:

KMEANS[data0_, clusters0_] := 
 Module[{data = data0, clusters = clusters0},
  n = Length[data];
  last = 0;
  label = RandomInteger[clusters, n];
  While[MatrixQ[label - last, PossibleZeroQ] != True,
   e = SparseArray[ConstantArray[0, {n, k}]];
   SET[index0_] := Module[{index = index0},
     e[[index[[1]], index[[2]]]] = 1;
     ];
   Map[SET, label]

   ]
  ]

How could this be done nicely?

$\endgroup$
  • 1
    $\begingroup$ I wrote an implementation of k-means in this answer. $\endgroup$ – rm -rf Sep 20 '14 at 21:43
  • 2
    $\begingroup$ k-means is also one of the options in the ClusteringComponents function. $\endgroup$ – bill s Sep 20 '14 at 22:02
  • 3
    $\begingroup$ Since people here are much more likely to be familiar with Mathematica functions than MATLAB ones I think you should include specific descriptions of what the MATLAB functions do that you wish to implement in Mathematica. $\endgroup$ – Mr.Wizard Sep 21 '14 at 8:56
  • $\begingroup$ spdiags extracts all the non-zero diagonals from a matrix. $\endgroup$ – dr.blochwave Sep 21 '14 at 10:07
  • $\begingroup$ bsxfun performs element-wise operations. e.g. in your example, bsxfun(@minus,m'*X,dot(m,m,1)'/2) will subtract the result of dot(m,m,1)'/2 from m'*X. $\endgroup$ – dr.blochwave Sep 21 '14 at 10:09

Browse other questions tagged or ask your own question.