Home > chronux_2_00 > spikesort > utility > datatools > pairdist.m

pairdist

PURPOSE ^

PAIRDIST Computes a pairwise Euclidean distance matrix.

SYNOPSIS ^

function dists = pairdist(X,varargin)

DESCRIPTION ^

PAIRDIST          Computes a pairwise Euclidean distance matrix.
   DISTS = PAIRDIST(X) returns a symmetric positive definite matrix DISTS
   such that the DISTS(i,j) is the Euclidean distance between the vectors
   X(i,:) and X(j,:).  X must be a real-valued matrix.

   DISTS = PAIRDIST(X,Y), where X is an M x D matrix and Y is N x D,
   returns an M x N matrix DISTS such that DISTS(i,j) is the Euclidean
   distance between X(i,:) and Y(j,:).  X and Y must be real-valued.

   The algorithm used by default utilizes the expansion
                    (x-y)'(x-y) == x'x + y'y - 2x'y,
   because the right hand side uses fewer floating point operations.
   However, round-off error with this technique may produce small but
   non-zero (even negative) values when x == y.

   DISTS = PAIRDIST(X,Y,'safe') indicates that it is possible for
   the ith row of X to be identical to the jth row of Y.  This uses a
   slower algorithm, but guarantees that DISTS(i,j) == 0 in these cases.
   For the special case of PAIRDIST(X), it is not necessary to specify
   the 'safe' flag if the only potential zero distances are those along
   the diagonal of DISTS.

   DISTS = PAIRDIST(..., 'nosqrt') returns DISTS as above, except that
   the squared distances are returned.  The algorithm to compute the
   distances finds the squared distances in an intermediate step, so this
   calculation is faster than returning the Euclidean distance proper.

   DISTS = PAIRDIST(..., 'reuse') attempts to reuse memory from an
   earlier call to PAIRDIST.  When DISTS is a large matrix, the resulting
   time savings can be significant.  However, this option can result in
   unexpected Matlab behavior for the returned variable DISTS.  In
   particular, clearing DISTS in the calling workspace will not release
   the memory associated with that variable; to release the memory, you
   must run the command 'clear functions'.  Further, DISTS may be
   unexpectedly modified by later calls to PAIRDIST.  For example,

       A = PAIRDIST(X1,Y1);         % Look at the value of A(1,2)
       B = PAIRDIST(X2,Y2,'reuse'); % The value of A(1,2) will change
                                    % here even though A was not assigned

   If this behavior is undesirable, make a copy of the returned distance
   matrix before calling PAIRDIST again.

CROSS-REFERENCE INFORMATION ^

This function calls: This function is called by:

SOURCE CODE ^

0001 function dists = pairdist(X,varargin)
0002 %PAIRDIST          Computes a pairwise Euclidean distance matrix.
0003 %   DISTS = PAIRDIST(X) returns a symmetric positive definite matrix DISTS
0004 %   such that the DISTS(i,j) is the Euclidean distance between the vectors
0005 %   X(i,:) and X(j,:).  X must be a real-valued matrix.
0006 %
0007 %   DISTS = PAIRDIST(X,Y), where X is an M x D matrix and Y is N x D,
0008 %   returns an M x N matrix DISTS such that DISTS(i,j) is the Euclidean
0009 %   distance between X(i,:) and Y(j,:).  X and Y must be real-valued.
0010 %
0011 %   The algorithm used by default utilizes the expansion
0012 %                    (x-y)'(x-y) == x'x + y'y - 2x'y,
0013 %   because the right hand side uses fewer floating point operations.
0014 %   However, round-off error with this technique may produce small but
0015 %   non-zero (even negative) values when x == y.
0016 %
0017 %   DISTS = PAIRDIST(X,Y,'safe') indicates that it is possible for
0018 %   the ith row of X to be identical to the jth row of Y.  This uses a
0019 %   slower algorithm, but guarantees that DISTS(i,j) == 0 in these cases.
0020 %   For the special case of PAIRDIST(X), it is not necessary to specify
0021 %   the 'safe' flag if the only potential zero distances are those along
0022 %   the diagonal of DISTS.
0023 %
0024 %   DISTS = PAIRDIST(..., 'nosqrt') returns DISTS as above, except that
0025 %   the squared distances are returned.  The algorithm to compute the
0026 %   distances finds the squared distances in an intermediate step, so this
0027 %   calculation is faster than returning the Euclidean distance proper.
0028 %
0029 %   DISTS = PAIRDIST(..., 'reuse') attempts to reuse memory from an
0030 %   earlier call to PAIRDIST.  When DISTS is a large matrix, the resulting
0031 %   time savings can be significant.  However, this option can result in
0032 %   unexpected Matlab behavior for the returned variable DISTS.  In
0033 %   particular, clearing DISTS in the calling workspace will not release
0034 %   the memory associated with that variable; to release the memory, you
0035 %   must run the command 'clear functions'.  Further, DISTS may be
0036 %   unexpectedly modified by later calls to PAIRDIST.  For example,
0037 %
0038 %       A = PAIRDIST(X1,Y1);         % Look at the value of A(1,2)
0039 %       B = PAIRDIST(X2,Y2,'reuse'); % The value of A(1,2) will change
0040 %                                    % here even though A was not assigned
0041 %
0042 %   If this behavior is undesirable, make a copy of the returned distance
0043 %   matrix before calling PAIRDIST again.
0044 
0045 %%%%%%%%%%%%%%%%%%%%%%%%%%%% Parse Inputs %%%%%%%%%%%%%%%%%%%%%%%%%%%%
0046 Y = [];   takeSqrt = 1;   reuseMem = 0;  useSafe = 0;
0047 while (length(varargin) > 0)
0048     tail = varargin{end};  varargin = varargin(1:end-1);  % chomp last arg
0049     if (ischar(tail) && strcmpi(tail, 'nosqrt'))
0050         takeSqrt = 0;
0051     elseif (ischar(tail) && strcmpi(tail, 'reuse')),
0052         reuseMem = 1;
0053     elseif (ischar(tail) && strcmpi(tail, 'safe')),
0054         useSafe = 1;
0055     elseif (isa(tail, 'double'))
0056         Y = tail;   break;    % this should be the leftmost argument
0057     else
0058         error('Unknown argument.');
0059     end
0060 end
0061 if (length(varargin) > 0),  error('Too many arguments.');  end;
0062 if (isempty(Y)),  Y = X;  end;   % self-distance computation
0063 
0064 [M,D1] = size(X);
0065 [N,D2] = size(Y);
0066 if (D1~=D2),  error('X and Y must have the same number of columns.');  end;
0067 if (~isreal(X) || ~isreal(Y) || ~isa(X,'double') || ~isa(Y,'double'))
0068     error('Input matrices must be real-valued matrices of type double.');
0069 end
0070     
0071 %%%%%%%%%%%%%%%%%%%%%%%%%%% Do the Computation %%%%%%%%%%%%%%%%%%%%%%%%%%
0072 dists = CORE_pairdist(X,Y,takeSqrt,reuseMem,useSafe);

Generated on Fri 15-Aug-2008 11:35:42 by m2html © 2003