function f = normalizerange(m,targetmin,targetmax,sourcemin,sourcemax,chop,mode,fast) <m> is a matrix <targetmin> is the minimum desired value. can be a scalar or a matrix the same size as <m>. <targetmax> is the maximum desired value. can be a scalar or a matrix the same size as <m>. <sourcemin> (optional) sets the min value of <m>. can be a scalar or a matrix the same size as <m>. default is [], which means to find the actual minimum. special case is NaN which means -nanmax(abs(m(:))). <sourcemax> (optional) sets the max value of <m>. can be a scalar or a matrix the same size as <m>. default is [], which means to find the actual maximum. special case is NaN which means nanmax(abs(m(:))). <chop> (optional) is whether to chop off the ends such that there are no values below <targetmin> nor above <targetmax>. default: 1. <mode> (optional) is 0 means normal operation 1 means interpret <sourcemin> and <sourcemax> as multipliers for the std of m(:). in this mode, the default for <sourcemin> and <sourcemax> is -3 and 3, respectively, which means to use mn-3*sd and mn+3*sd for the min and max value of <m>, respectively. note that in this mode, <sourcemin> and <sourcemax> cannot be NaN. default: 0. <fast> (optional) means we have a guarantee that all inputs are fully specified and <m> is not empty. return <m> scaled and translated such that [<sourcemin>,<sourcemax>] maps to [<targetmin>,<targetmax>]. if <chop>, we also threshold values below <targetmin> and values above <targetmax>. note that if <sourcemin> is ever equal to <sourcemax>, then we die with an error. note that <chop> has no effect if <sourcemin> and <sourcemax> aren't specified. we deal with NaNs in <m> gracefully. examples: isequal(normalizerange([1 2 3],0,1),[0 1/2 1]) isequal(normalizerange([1 2 3],0,1,2,3,1),[0 0 1]) isequalwithequalnans(normalizerange([1 2 NaN],0,1,0,4),[1/4 2/4 NaN])
0001 function f = normalizerange(m,targetmin,targetmax,sourcemin,sourcemax,chop,mode,fast) 0002 0003 % function f = normalizerange(m,targetmin,targetmax,sourcemin,sourcemax,chop,mode,fast) 0004 % 0005 % <m> is a matrix 0006 % <targetmin> is the minimum desired value. can be a scalar or a matrix the same size as <m>. 0007 % <targetmax> is the maximum desired value. can be a scalar or a matrix the same size as <m>. 0008 % <sourcemin> (optional) sets the min value of <m>. can be a scalar or a matrix the same size as <m>. 0009 % default is [], which means to find the actual minimum. special case is NaN which means -nanmax(abs(m(:))). 0010 % <sourcemax> (optional) sets the max value of <m>. can be a scalar or a matrix the same size as <m>. 0011 % default is [], which means to find the actual maximum. special case is NaN which means nanmax(abs(m(:))). 0012 % <chop> (optional) is whether to chop off the ends such that there are no values below <targetmin> nor 0013 % above <targetmax>. default: 1. 0014 % <mode> (optional) is 0015 % 0 means normal operation 0016 % 1 means interpret <sourcemin> and <sourcemax> as multipliers for the std of m(:). 0017 % in this mode, the default for <sourcemin> and <sourcemax> is -3 and 3, respectively, 0018 % which means to use mn-3*sd and mn+3*sd for the min and max value of <m>, respectively. 0019 % note that in this mode, <sourcemin> and <sourcemax> cannot be NaN. 0020 % default: 0. 0021 % <fast> (optional) means we have a guarantee that all inputs are fully specified and <m> is not empty. 0022 % 0023 % return <m> scaled and translated such that [<sourcemin>,<sourcemax>] maps to 0024 % [<targetmin>,<targetmax>]. if <chop>, we also threshold values below <targetmin> 0025 % and values above <targetmax>. 0026 % 0027 % note that if <sourcemin> is ever equal to <sourcemax>, then we die with an error. 0028 % note that <chop> has no effect if <sourcemin> and <sourcemax> aren't specified. 0029 % 0030 % we deal with NaNs in <m> gracefully. 0031 % 0032 % examples: 0033 % isequal(normalizerange([1 2 3],0,1),[0 1/2 1]) 0034 % isequal(normalizerange([1 2 3],0,1,2,3,1),[0 0 1]) 0035 % isequalwithequalnans(normalizerange([1 2 NaN],0,1,0,4),[1/4 2/4 NaN]) 0036 0037 % if <fast>, skip stuff for speed 0038 if nargin ~= 8 0039 0040 % check empty case 0041 if isempty(m) 0042 f = m; 0043 return; 0044 end 0045 0046 % input 0047 if ~exist('sourcemin','var') || isempty(sourcemin) 0048 sourcemin = []; 0049 end 0050 if ~exist('sourcemax','var') || isempty(sourcemax) 0051 sourcemax = []; 0052 end 0053 if ~exist('chop','var') || isempty(chop) 0054 chop = 1; 0055 end 0056 if ~exist('mode','var') || isempty(mode) 0057 mode = 0; 0058 end 0059 0060 end 0061 0062 % calc 0063 skipchop = (mode==0 && (isempty(sourcemin) && isempty(sourcemax))) || (mode==0 && isnan(sourcemin) && isnan(sourcemax)); % don't bother chopping in these cases 0064 switch mode 0065 case 0 0066 if isempty(sourcemin) 0067 sourcemin = nanmin(m(:)); 0068 end 0069 if isempty(sourcemax) 0070 sourcemax = nanmax(m(:)); 0071 end 0072 if isnan(sourcemin) || isnan(sourcemax) 0073 temp = nanmax(abs(m(:))); 0074 if isnan(sourcemin) 0075 sourcemin = -temp; 0076 end 0077 if isnan(sourcemax) 0078 sourcemax = temp; 0079 end 0080 end 0081 case 1 0082 if isempty(sourcemin) 0083 sourcemin = -3; 0084 end 0085 if isempty(sourcemax) 0086 sourcemax = 3; 0087 end 0088 mn = nanmean(m(:)); 0089 sd = nanstd(m(:)); 0090 sourcemin = mn+sourcemin*sd; 0091 sourcemax = mn+sourcemax*sd; 0092 end 0093 0094 % sanity check 0095 if any(sourcemin==sourcemax) 0096 error('sourcemin and sourcemax are the same in at least one case'); 0097 end 0098 0099 % go ahead and chop 0100 if chop && ~skipchop 0101 temp = isnan(m); 0102 m = max(min(m,sourcemax),sourcemin); 0103 m(temp) = NaN; % preserve NaNs 0104 end 0105 0106 % want to do: f = (m-sourcemin) .* (targetmax-targetmin)./(sourcemax-sourcemin) + targetmin 0107 val = (targetmax-targetmin)./(sourcemax-sourcemin); 0108 f = m.*val - (sourcemin.*val - targetmin); % like this for speed