【问题标题】:How to normalize / denormalize a vector to range [-1;1]如何将向量规范化/非规范化到范围 [-1;1]
【发布时间】:2011-06-08 17:59:40
【问题描述】:

我如何规范化一个向量到[-1;1]范围内

我想使用函数norm,因为它会更快。

还请告诉我如何在规范化之后去规范化那个向量?

【问题讨论】:

    标签: matlab normalization denormalization


    【解决方案1】:

    一个简单的解决方案是使用现成的 MATLAB 函数:

    mapminmax
    

    通过将行最小值和最大值映射到 [-1 1] 来处理矩阵

    例子:

    x1 = [1 2 4; 1 1 1; 3 2 2; 0 0 0]
    [y1,PS] = mapminmax(x1)
    

    在归一化后对该向量进行反归一化

    x1_again = mapminmax('reverse',y1,PS)
    

    【讨论】:

      【解决方案2】:

      最新的答案是使用 Matlab R2017b 中引入的 rescale 函数。要将向量 A 标准化为范围 -1:1,您可以运行:

      A = rescale(A, -1, 1);
      

      您可以通过预先保存最小值和最大值然后再次运行重新调整来撤消此操作:

      maxA = max(A(:));
      minA = min(A(:));
      A = rescale(A, -1, 1);
      % use the normalised A
      A = rescale(A, minA, maxA);
      

      【讨论】:

        【解决方案3】:

        基于 Jonas 的答案的扩展答案如下。它允许根据向量中是否存在负数和正数进行自动归一化,或者手动选择所需的归一化类型。函数下方是一个测试脚本。

        归一化函数

        function [vecN, vecD] = normVec(vec,varargin)
        % Returns a normalize vector (vecN) and "de-nomralized" vector (vecD). The
        % function detects if both positive and negative values are present or not
        % and automatically normalizes between the appropriate range (i.e., [0,1],
        % [-1,0], or [-1,-1].
        % Optional argument allows control of normalization range:
        % normVec(vec,0) => sets range based on positive/negative value detection
        % normVec(vec,1) => sets range to [0,1]
        % normVec(vec,2) => sets range to [-1,0]
        % normVec(vec,3) => sets range to [-1,1]
        
        %% Default Input Values
        % Check for proper length of input arguments
        numvarargs = length(varargin);
        if numvarargs > 1
            error('Requires at most 1 optional input');
        end
        
        % Set defaults for optional inputs
        optargs = {0};
        
        % Overwrite default values if new values provided
        optargs(1:numvarargs) = varargin;
        
        % Set input to variable names
        [setNorm] = optargs{:};
        
        %% Normalize input vector
        % get max and min
        maxVec = max(vec);
        minVec = min(vec);
        
        if setNorm == 0
            % Automated normalization
            if minVec >= 0
                % Normalize between 0 and 1
                vecN = (vec - minVec)./( maxVec - minVec );
                vecD = minVec + vecN.*(maxVec - minVec);
            elseif maxVec <= 0
                % Normalize between -1 and 0
                vecN = (vec - maxVec)./( maxVec - minVec );
                vecD = maxVec + vecN.*(maxVec - minVec);
            else
                % Normalize between -1 and 1
                vecN = ((vec-minVec)./(maxVec-minVec) - 0.5 ) *2;
                vecD = (vecN./2+0.5) * (maxVec-minVec) + minVec;
            end
        elseif setNorm == 1
            % Normalize between 0 and 1
            vecN = (vec - minVec)./( maxVec - minVec );
            vecD = minVec + vecN.*(maxVec - minVec);
        elseif setNorm == 2
            % Normalize between -1 and 0
            vecN = (vec - maxVec)./( maxVec - minVec );
            vecD = maxVec + vecN.*(maxVec - minVec);
        elseif setNorm == 3
            % Normalize between -1 and 1
            vecN = ((vec-minVec)./(maxVec-minVec) - 0.5 ) *2;
            vecD = (vecN./2+0.5) * (maxVec-minVec) + minVec;
        else
            error('Unrecognized input argument varargin. Options are {0,1,2,3}');
        end
        

        测试函数的脚本

        % Define vector
        x=linspace(0,4*pi,25);
        y = sin(x);
        ya=sin(x); yb=y+10; yc=y-10;
        
        % Normalize vector
        ya0=normVec(ya); yb0=normVec(yb); yc0=normVec(yc);
        ya1=normVec(ya,1); yb1=normVec(yb,1); yc1=normVec(yc,1);
        ya2=normVec(ya,2); yb2=normVec(yb,2); yc2=normVec(yc,2);
        ya3=normVec(ya,3); yb3=normVec(yb,3); yc3=normVec(yc,3);
        
        % Plot results
        figure(1)
        subplot(2,2,1)
        plot(x,ya0,'k',x,yb0,'ro',x,yc0,'b^')
        title('Auto Norm-Range')
        subplot(2,2,2)
        plot(x,ya1,'k',x,yb1,'ro',x,yc1,'b^')
        title('Manual Norm-Range: [0,1]')
        subplot(2,2,3)
        plot(x,ya2,'k',x,yb2,'ro',x,yc2,'b^')
        title('Manual Norm-Range: [-1,0]')
        subplot(2,2,4)
        plot(x,ya3,'k',x,yb3,'ro',x,yc3,'b^')
        title('Manual Norm-Range: [-1,1]')
        

        【讨论】:

          【解决方案4】:

          norm 对向量进行归一化,使其平方和为 1。

          如果要对向量进行归一化,使其所有元素都介于 0 和 1 之间,则需要使用最小值和最大值,然后可以使用它们再次进行反规范化。

          %# generate some vector
          vec = randn(10,1);
          
          %# get max and min
          maxVec = max(vec);
          minVec = min(vec);
          
          %# normalize to -1...1
          vecN = ((vec-minVec)./(maxVec-minVec) - 0.5 ) *2;
          
          %# to "de-normalize", apply the calculations in reverse
          vecD = (vecN./2+0.5) * (maxVec-minVec) + minVec
          

          【讨论】:

          • 如何使用相同的代码在 0 和 1 之间进行规范化?
          • @Shyamkkhadka:使用下方ScottG提供的代码,或使用((vec-minVec)./(maxVec-minVec))
          猜你喜欢
          • 2015-01-10
          • 2013-08-21
          • 2016-05-13
          • 2018-06-06
          • 2021-06-13
          • 2020-04-06
          • 2012-05-22
          • 1970-01-01
          相关资源
          最近更新 更多