from
pushNaNs
by Daniel
Pushes NaNs to the bottom of each column of X.
|
| pushnans( X,truncate )
|
function X = pushnans( X,truncate )
% X = PUSHNANS(X,truncate)
%
% Pushes nans to the bottom of each column of X.
% The second input is an optional flag. If true, the whole-nan rows at the
% bottom of X are removed.
%
% DM, Apr 2013
%
NAN_THRESHOLD_FRACTION = 0.9; %I haven't actually optimised this value, proably system and version dependant
if sum(sum(isnan(X)))/numel(X) > NAN_THRESHOLD_FRACTION %Note we could do a random sample of X rather than all of it, but this is already pretty fast
pickOutNonNansMethod %when there are few non-nans, do this
else
sortAllMethod %when there are loads of non-nans do this
end
function sortAllMethod
[s1,s2] = size(X);
%get a matrix of row indices with indices refering to non-nans at the top of the columns in the original order
[~,row] = sort(isnan(X));
%use the row indicies and manually calcualte the full-index to rearange X
X = X(bsxfun(@plus,uint32((0:s2-1)*s1),uint32(row)));
if exist('truncate','var') && truncate
s2 = max(sum(~isnan(X)));
X(s2+1:end,:) = [];
end
end
function pickOutNonNansMethod
%In this method we use find to get a list of column indices for all the
%non-nan values. We then use "manually" work out the row indicies
one = uint32(1);
%get a list of non-nan vals and their column indices
goodVal = X(~isnan(X));
[~, goodIndCol] = find(~isnan(X));
goodIndCol = uint32(goodIndCol);
%we'll need these dimensions
[s1,s2] = size(X);
s0 = uint32(numel(goodIndCol));
%work out the row indices for each of the non-nan vals in our list
isColHead = [single(1) ; goodIndCol(1:end-1)~=goodIndCol(2:end)];
indColHead = uint32(cumsum(isColHead));
colHead = uint32(find(isColHead));
goodRowInd = (one:s0)' - colHead(indColHead) + one;
%prepare a new whole-nan matrix of the correct size
if exist('truncate','var') && truncate
s1 = max(goodRowInd);
end
X = nan(s1,s2);
%use our lovely indices to place the non-nans at the top of the rows
X((goodIndCol-one)*uint32(s1) + goodRowInd) = goodVal;
end
end
%}
|
|
Contact us