熵權法求權重原理詳細步驟附matlab代碼


熵權法是一種在綜合考慮各因素提供信息量的 基礎上計算一個綜合指標的數學方法。作為客觀綜合定權法,其主要根據各指標傳遞給決策者的信息量大小來確定權重。根據信息論基本原理,信息是系統有序程度的度量;而熵則是系統無序程度的度量。因此,可用系 統熵來反映其提供給決策者的信息量大小,系統熵可通過熵權法得到。

熵值法確定權重的基本步驟:

  1. 選取n個樣本,m個指標,則為第i個樣本的第j個指標的數值(i=1, 2…, nj=1,2,…, m);
  2. 指標的歸一化處理:異質指標同質化
    由於各項指標的計量單位並不統一,因此在用它們計算綜合指標前,先要對它們進行標准化處理,即把指標的絕對值轉化為相對值,並令 ,從而解決各項不同質指標值的同質化問題。而且,由於正向指標(極大型指標)和負向指標(極小型指標)數值代表的含義不同(正向指標數值越高越好,負向指標數值越低越好),因此,對於高低指標我們用不同的算法進行數據標准化處理。其具體方法如下:
    正向指標:
    負向指標:
    為第 i個樣本的第 j個指標的數值( i=1, 2…,  nj=1, 2,…,  m)。為了方便起見,歸一化后的數據仍記為 ;   其他類型指標如下圖所示,在運行程序中有對應處理代碼。

           3.計算第j項指標下第i個樣本占該指標的比重:

           4.計算第j項指標的熵值:其中. 滿足;

           5.計算信息熵冗余度:

           6.計算各項指標的權值:

           7. 計算各樣本的綜合得分:

       運行代碼:

clc;clear;
%  實現用熵值法求各指標(列)的權重及各數據行的得分
% x為原始數據矩陣, 一行代表一個樣本, 每列對應一個指標
% s返回各行得分, w返回各列權重
load('data_water_quality.mat')%載入數據
x=X;     %X為工作表中的樣本數據
%% 數據的正向化處理
[n,m]=size(x); % X中有n個樣本, m個指標
disp(['共有' num2str(n) '個評價對象, ' num2str(m) '個評價指標']) 
Judge = input(['' num2str(m) '個指標是否需要經過正向化處理,需要請輸入1 ,不需要輸入0:  ']);

if Judge == 1
    Position = input('請輸入需要正向化處理的指標所在的列,例如第2、3、6三列需要處理,那么你需要輸入[2,3,6]: '); %[2,3,4]
    disp('請輸入需要處理的這些列的指標類型(1:極小型, 2:中間型, 3:區間型) ')
    Type = input('例如:第2列是極小型,第3列是區間型,第6列是中間型,就輸入[1,3,2]:  '); %[2,1,3]
    % 注意,Position和Type是兩個同維度的行向量
    for i = 1 : size(Position,2)  %這里需要對這些列分別處理,因此我們需要知道一共要處理的次數,即循環的次數
        X(:,Position(i)) = Positivization(X(:,Position(i)),Type(i),Position(i));
    % Positivization是我們自己定義的函數,其作用是進行正向化,其一共接收三個參數
    % 第一個參數是要正向化處理的那一列向量 B(:,Position(i))   X(:,n)表示取第n列的全部元素
    % 第二個參數是對應的這一列的指標類型(1:極小型, 2:中間型, 3:區間型)
    % 第三個參數是告訴函數我們正在處理的是原始矩陣中的哪一列
    % 該函數有一個返回值,它返回正向化之后的指標,我們可以將其直接賦值給我們原始要處理的那一列向量
    end
    disp('正向化后的矩陣 X =  ')
    disp(X)
end
%% 數據的歸一化處理
% Matlab2010b,2011a,b版本都有bug,需如下處理. 其它版本直接用[X,ps]=mapminmax(x',0,1);即可

[B,ps]=mapminmax(X');
ps.ymin=0.002; % 歸一化后的最小值
ps.ymax=0.996; % 歸一化后的最大值
ps.yrange=ps.ymax-ps.ymin; % 歸一化后的極差,若不調整該值, 則逆運算會出錯
B=mapminmax(X',ps);
% mapminmax('reverse',xx,ps); % 反歸一化, 回到原數據
B=B';  % B為歸一化后的數據
%% 計算第j個指標下,第i個記錄占該指標的比重p(i,j)
for i=1:n
    for j=1:m
        p(i,j)=B(i,j)/sum(X(:,j));
    end
end
%% 計算第j個指標的熵值e(j)
k=1/log(n);
for j=1:m
    e(j)=-k*sum(p(:,j).*log(p(:,j)));
end
d=ones(1,m)-e;  % 計算信息熵冗余度
w=d./sum(d);    % 求權值w
s=w*p';         % 求綜合得分[\code]
disp("信息冗余度為");disp(d)
disp("各樣本綜合得分s為");disp(s);
disp("各指標權重w為");disp(w);

     正向化函數代碼

(1)Positivization

% function [輸出變量] = 函數名稱(輸入變量)  
% 函數的中間部分都是函數體
% 函數的最后要用end結尾
% 輸出變量和輸入變量可以有多個,用逗號隔開
% function [a,b,c]=test(d,e,f)
%     a=d+e;
%     b=e+f;
%     c=f+d;
% end
% 自定義的函數要單獨放在一個m文件中,不可以直接放在主函數里面(和其他大多數語言不同)

function [posit_x] = Positivization(x,type,i)
% 輸入變量有三個:
% x:需要正向化處理的指標對應的原始列向量
% type: 指標的類型(1:極小型, 2:中間型, 3:區間型)
% i: 正在處理的是原始矩陣中的哪一列
% 輸出變量posit_x表示:正向化后的列向量
    if type == 1  %極小型
        disp(['' num2str(i) '列是極小型,正在正向化'] )
        posit_x = Min2Max(x);  %調用Min2Max函數來正向化
        disp(['' num2str(i) '列極小型正向化處理完成'] )
        disp('~~~~~~~~~~~~~~~~~~~~分界線~~~~~~~~~~~~~~~~~~~~')
    elseif type == 2  %中間型
        disp(['' num2str(i) '列是中間型'] )
        best = input('請輸入最佳的那一個值: ');
        posit_x = Mid2Max(x,best);
        disp(['' num2str(i) '列中間型正向化處理完成'] )
        disp('~~~~~~~~~~~~~~~~~~~~分界線~~~~~~~~~~~~~~~~~~~~')
    elseif type == 3  %區間型
        disp(['' num2str(i) '列是區間型'] )
        a = input('請輸入區間的下界: ');
        b = input('請輸入區間的上界: '); 
        posit_x = Inter2Max(x,a,b);
        disp(['' num2str(i) '列區間型正向化處理完成'] )
        disp('~~~~~~~~~~~~~~~~~~~~分界線~~~~~~~~~~~~~~~~~~~~')
    else
        disp('沒有這種類型的指標,請檢查Type向量中是否有除了1、2、3之外的其他值')
    end
end

(2)Inter2Max

function [posit_x] = Inter2Max(x,a,b)
    r_x = size(x,1);  % row of x 
    M = max([a-min(x),max(x)-b]);
    posit_x = zeros(r_x,1);   %zeros函數用法: zeros(3)  zeros(3,1)  ones(3)
    % 初始化posit_x全為0  初始化的目的是節省處理時間
    for i = 1: r_x
        if x(i) < a
           posit_x(i) = 1-(a-x(i))/M;
        elseif x(i) > b
           posit_x(i) = 1-(x(i)-b)/M;
        else
           posit_x(i) = 1;
        end
    end
end

(3)Mid2Max

function [posit_x] = Mid2Max(x,best)
    M = max(abs(x-best));
    posit_x = 1 - abs(x-best) / M;
end

(4)Min2Max

function [posit_x] = Min2Max(x)
    posit_x = max(x) - x;
     %posit_x = 1 ./ x;    %如果x全部都大於0,也可以這樣正向化
end

 

運行結果如下圖所示:

 

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM