HanyangHe95's picture
Upload 20 files
9677843 verified
function [ds,inds] = knnCPU(R,Q,k,maxMem)
% Find the k nearest neighbors for each element of the query set Q among
% the points in the reference set R
% Q is Nxd where N is the number of query points and d is the dimension
% R is Mxd where M is the number of reference points and d is the dimension
% k is the number of nearest neighbors desired
% maxMem is the number of GB of ram knnCPU can use
% ds is Nxk and contains the distances to the k nearest neighbors.
% inds is Nxk and contains the indices of the k nearest neighbors.
if (nargin<4)
maxMem = 2;
end
M = size(R,1);
N = size(Q,1);
maxArray = (maxMem*2500)^2;
blockSize = floor(maxArray/M);
blocks = floor(N/blockSize);
ds = zeros(N,k);
inds = zeros(N,k);
Nr = sum(R.^2,2);
Nq = sum(Q.^2,2);
for b = 1:blocks
dtemp = -2*R*Q((b-1)*blockSize + 1:b*blockSize,:)';
dtemp = bsxfun(@plus,dtemp,Nr);
dtemp = bsxfun(@plus,dtemp,Nq((b-1)*blockSize + 1:b*blockSize)');
[dst,indst] = sort(dtemp,1);
ds((b-1)*blockSize + 1:b*blockSize,:) = dst(1:k,:)';
inds((b-1)*blockSize + 1:b*blockSize,:) = indst(1:k,:)';
end
if (blocks*blockSize < N)
dtemp = -2*R*Q(blocks*blockSize + 1:N,:)';
dtemp = bsxfun(@plus,dtemp,Nr);
dtemp = bsxfun(@plus,dtemp,Nq(blocks*blockSize + 1:N)');
[dst,indst] = sort(dtemp,1);
ds(blocks*blockSize + 1:N,:) = dst(1:k,:)';
inds(blocks*blockSize + 1:N,:) = indst(1:k,:)';
end
ds = real(sqrt(ds));
end