function A = BestMatchingNeurons(X, W, N1, N2)
% BestMatchingNeurons: Matrix of best matching neurons for Self-Organizing Map
% A = BestMatchingNeurons(X, W, N1, N2)
%
% WARNING: WE ASSUME A SPARSELY-MATCHED SOM; if two input vectors match the same
% location, we force the second one to be associated with the second best
% match. If there are more than 3 input vectors that match the same
% location, only two of them will be associated with labels.
%
% This function creates matrix A which stores the index of each input
% vector in the location of the best matching neuron in the SOM map.
% It has the same size as the SOM map.
%
% INPUTS:
% X: L x M matrix of L input vectors, each with M features
% W: N x M matrix of N SOM-trained neurons, each with M features
% (i.e., linear form of trained SOM with M component planes)
% N1: scalar representing the first dimension of the rectangular SOM map
% N2: scalar representing the second dimension of the rectangular SOM map
%
% OUTPUT:
% A: N1 x N2 matrix of input indices stored in the best matching
% neurons locations on the map
%
%
% Authors and Contact information:
% Narine Manukyan
% University e-mail: Narine.Manukyan@uvm.edu
% Lifetime email: narulka22000@gmail.com
%
% Margaret J. Eppstein
% e-mail: Maggie.Eppstein@uvm.edu
%
% Department of Computer Science
% University of Vermont
% Burlington Vermont, 05401
%
% Code posted to Matlab File Exchange: 15-March-2012
L = size(X,1); % Number of input vectors (each of length M)
% Initialize a 2D matrix that stores the index of each input vector
% in the location of the best matching neurons in the SOM map.
A = zeros(N1,N2); %we'll mark with index number which locations are taken
for i = 1:L %for each input vector
ind = index_of_closest(X(i,:), W, 1);
j = ceil(ind/N1);
k = mod(ind,N1);
if k == 0
k = N1;
end
if A(k,j) == 0 % see if anyone else already matched this neuron
A(k,j)=i; %record that input vector i matched here
else % find the second best matching neuron; we do this to avoid conflicts
ind2 = index_of_closest(X(i,:), W, 2);
j = ceil(ind2/N1);
k = mod(ind2,N1);
if k == 0
k = N1;
end
if A(k,j) == 0 %if not available, this input vector won't be given a location
A(k,j)=i;%record that input vector i matched here
end
end
end
end