ILPD(印度肝病患者)分類BP算法和KNN

聲明:本篇文章是本人課程作業的內容,只提供平時學習參考使用,請勿轉載。

介紹:數據挖掘

來源:kaibo_lei_ZZU

ILPD數據集

ILPD數據集來自美國加州大學一個統計學習相關的網站上(UCI)數據集的名稱叫做Indian Liver Patient Dataset印度肝病患者數據集,這個數據集由三個印度的教授收集自印度安得拉邦的東北部,包含了416個肝癌病人和167個非肝癌病人共計583個肝病患者的病歷數據記錄。583個病人中包含441名男性病人和142名女性病人,其中任何年齡超過89歲的患者都被列爲年齡90。
在這裏插入圖片描述

ILPD數據集屬性描述

在ILPD數據集中,該數據集包含416個肝臟患者記錄和167個非肝臟患者記錄。共計10個主要屬性,以及583個樣本數,裏面有肝病患者和非肝病患者的記錄。
具體屬性描述如下表:
在這裏插入圖片描述

原始數據集展示

該數據集是一個CSV格式的數據文件,一共有538行11列數據。
下圖是對原始數據集的前25條數據展示:

在這裏插入圖片描述
數據的第一列代表患者年齡,第二列爲患者性別。在這裏性別是一個字符串形式的表示,我們在下面的數據分析中需要把數據轉換爲離散型的數據表示,可以方便我們的數據分析。數據的最後一行表示是否患病,1表示肝癌病人,2表示非肝癌病人。

數據處理

首先進行數據的簡單預處理,進行偏差檢測,即檢查導致偏差的因素,並識別離散值與噪聲值。然後進行數據清洗,即處理缺失值與噪聲,通過觀察數據集我們可以發現在數據集的第二列,性別表示中男性是male表示,女性是female表示,爲了能讓提高我們的分類準確率,這裏需要進行替換,男性male用1表示,female用2來表示。
處理後的數據集表示如下:
在這裏插入圖片描述

1. BP(反向傳播)算法實現

BP算法描述

BP算法(Back-propagation),誤差反向傳播算法,它的基本思想:學習過程由信號的正向傳播(求損失)與誤差的反向傳播(誤差回傳)兩個過程組成。網絡的運行流程爲:當輸入一個樣例後,獲得該樣例的特徵向量,再根據權向量得到感知器的輸入值,然後使用函數計算出每個感知器的輸出,再將此輸出作爲下一層感知器的輸入,依次類推,直到輸出層。在多層的神經網絡中,誤差曲面可能有多個局部極小值,這意味着使用梯度下降算法找到的可能是局部極小值,而不是全局最小值。現在可以使用損失函數,這時可以根據損失函數來調整輸出結點中的輸入權向量,採用隨機梯度下降算法求解,然後從後向前逐層調整權重,這就是反向傳播算法計算的大致流程。
BP算法是一種有監督式的學習算法,其主要步驟是是輸入學習樣本,使用反向傳播算法對網絡的權值和偏差進行反覆的調整訓練,使輸出的向量與期望向量儘可能地接近,當網絡輸出層的誤差平方和小於指定的誤差時訓練完成,保存網絡的權值和偏差。具體步驟如下:
(1)初始化,隨機給定各連接權[w],[v]及閾值θi,rt。
(2)由給定的輸入輸出模式對計算隱層、輸出層各單元輸出bj=f(wijai-θj) ct=f(vjtbj-rt)
式中:bj爲隱層第j個神經元實際輸出;ct爲輸出層第t個神經元的實際輸出;wij爲輸入層至隱層的連接權;vjt爲隱層至輸出層的連接權。
dtk=(ytk-ct)ct(1-ct) ejk=[dtvjt] bj(1-bj)
(3)選取下一個輸入模式對返回第2步反覆訓練直到網絡設輸出誤差達到要求結束訓練。

實驗設計

(1)數據集劃分
在本數據集中,一共有538條數據,採用前400條數據進行參數訓練,後138條數據進行測試數據。

%讀取訓練數據
[NUM]=xlsread('shujv','A1:K400')
[A]=xlsread('shujv','A1:J400')

%讀取測試數據
[NUMT]=xlsread('shujv','A401:K583')
[C]=xlsread('shujv','A401:J583')

(2)算法步驟
將前400條數據作爲輸入,即(患者的年齡、患者的 性別性別、TB總膽紅素 、DB直接膽紅素、鹼性磷酸酶、氨基轉移酶、天冬氨酸氨基轉移酶、TP總標本、ALB白蛋白 、A / G比率白蛋白和球蛋白比率)。將對應的分類結果作爲輸出。並用matlab自帶的premnmx()函數將這些數據歸一化處理。

   %特徵值歸一化
    [input,minI,maxI] = premnmx( [A ]')  ;

通過樣本數據的訓練,不斷修正網絡權值和閾值使誤差函數沿負梯度方向下降,逼近期望輸出。
歸一化之後歐的數據形式如下:

訓練集歸一化:
在這裏插入圖片描述
測試集歸一化:
在這裏插入圖片描述
輸入輸出:

該模型由每組數據的各項指標作爲輸入,以分類結果作爲輸出輸入層的節點數爲10,輸出層的節點數爲1。
隱含層設計:
IW = net.IW{1,1};
LW = net.LW{2,1};
b1 = net.b{1}
b2 = net.b{2}
net是訓練得到的網絡,IW表示隱含層的權矩陣,維數 = 隱含層神經元個數 * 特徵數,LW表示隱含層權矩陣,維數 = 1 * 隱含層神經元個數,b1輸入層的閾值,b2隱含層的閾值。
輸入輸入以及隱含層的設計如下圖:

在這裏插入圖片描述
激勵函數:

BP神經網絡通常採用Sigmoid可微函數和線性函數作爲網絡的激勵函數。本文選擇S型正切函數tansig作爲隱層神經元的激勵函數。而由於網絡的輸出歸一到[ -1, 1]範圍內, 因此預測模型選取S 型對數函數tansig作爲輸出層神經元的激勵函數。
代碼如下:

out1 =1./(1+exp(-n1));    % tansig函數的表達式,out1表示輸入層的輸出結果
Z = (LW * out1) + repmat(b2,1,size(testInput,2)); 
out2 =1./(1+exp(-Z));    % tansig函數的表達式,out2表示輸入層的輸出結果

將訓練樣本數據歸一化後輸入網絡, 設定網絡隱層和輸出層激勵函數分別爲tansig, 網絡訓練函數爲traingdx, 網絡性能函數爲mse,隱層神經元數初設爲4。
設定網絡參數:

網絡迭代次數epochs爲10000次, 期望誤差goal爲0.01, 學習速率lr爲0.01,設置完畢,開始訓練。

%設置訓練參數
net.trainparam.epochs = 10000 ;
net.trainparam.goal = 0.01 ;
net.trainParam.lr = 0.01 ;

完整代碼

[NUM]=xlsread('shujv','A1:K400')
[A]=xlsread('shujv','A1:J400')
 
%特徵值歸一化
[input,minI,maxI] = premnmx( [A ]')  ;
%構造輸出矩陣
s = size(A,1);
output = zeros( s , 5  ) ;
for i = 1 : s 
   output( i , NUM(i,11)) = 1 ;
end
 
%創建神經網絡
net = newff( minmax(input) , [55 5] , { 'logsig' 'logsig' } , 'traingdx' ) ; 
 
%設置訓練參數
net.trainparam.show = 25 ;
net.trainparam.epochs = 10000 ;
net.trainparam.goal = 0.01 ;
net.trainParam.lr = 0.01 ;
 
%開始訓練
net = train( net, input , output' ) ;
 
%讀取測試數據
[NUMT]=xlsread('shujv','A401:K583')
[C]=xlsread('shujv','A401:J583')
%測試數據歸一化
testInput = tramnmx ( [C]' , minI, maxI ) ;
 
%仿真
Y = sim( net , testInput ) 
IW = net.IW{1,1};  % net是訓練得到的網絡,IW表示隱含層的權矩陣
                   % 維數 = 隱含層神經元個數 * 特徵數
LW = net.LW{2,1};  % LW表示隱含層權矩陣,維數 = 1 * 隱含層神經元個數
b1 = net.b{1}    % 輸入層的閾值
b2 = net.b{2}    % 隱含層的閾值
t=size(testInput,2)
u=IW * testInput;
n1 = (IW * testInput) + repmat(b1,1,size(testInput,2));
out1 =1./(1+exp(-n1));    % tansig函數的表達式,out1表示輸入層的輸出結果
Z = (LW * out1) + repmat(b2,1,size(testInput,2));        % purelin函數就是形如 y = x,所以直接可以得到out2
out2 =1./(1+exp(-Z));    % tansig函數的表達式,out1表示輸入層的輸出結果
out3=(1./(1+exp(-LW))) * (1./(1+exp(- IW)));
C= LW * IW;
out4=1./(1+exp(-C));
%統計識別正確率
[s1 , s2] = size( Y ) ;
hitNum = 0 ;
for i = 1 : s2
    [m , Index] = max( Y( : ,  i ) ) ;
    if( Index  ==  NUMT(i,11)   ) 
        hitNum = hitNum + 1 ; 
    end
end
sprintf('分類識別率是 %3.3f%%',100 * hitNum / s2 )

實驗結果分析

網絡訓練完成後,進行測試集測試訓練結果,與分類的正確率。
在這裏插入圖片描述
實驗結果:
網絡輸出誤差與訓練狀態
在這裏插入圖片描述圖 網絡訓練誤差
在這裏插入圖片描述圖 網絡訓練狀態

2. KNN算法分類

KNN算法步驟

KNN的算法原理描述與算法執行流程,我們在上一章的1.5章節已經介紹過,在這裏不再重複介紹。本章節主要是KNN算法在印度肝病分類實驗中的應用與分類效果。
KNN算法在分析印度肝病患者數據集時的具體算法步驟如下:
1)計算測試數據與各個訓練數據之間的距離,也就是計算數據集中前400條訓練數據與138條數據中各個屬性之間的距離。
2)按照距離的遞增關係進行排序,然後進行後續的座標點的選擇。
3)選取距離最小的K個點;
4)確定前K個點所在類別的出現頻率;
5)返回前K個點中出現頻率最高的類別作爲測試數據的預測分類。

實驗設計

(1)數據集分類
前400行前10列作爲訓練數據,第11列作爲測試標籤,後138行前10列作爲測試屬性,後138行第11列作爲測試標籤。
[NUM]=xlsread(‘shujv’,‘A1:J400’)
[A]=xlsread(‘shujv’,‘K1:K400’)

%讀取測試數據
[NUMT]=xlsread(‘shujv’,‘A401:J538’)
[C]=xlsread(‘shujv’,‘K401:K538’)

在這裏插入圖片描述

(2)數據歸一化
[mtrain,ntrain] = size(NUM);
[mtest,ntest] = size(NUMT);
dataset = [NUM;NUMT];
[dataset_scale,ps] = mapminmax(dataset’,0,1);
dataset_scale = dataset_scale’;
train_data = dataset_scale(1:mtrain,:);
test_data = dataset_scale( (mtrain+1):(mtrain+mtest),: );

(3)算法代碼
[NUM]=xlsread(‘shujv’,‘A1:J400’)
[A]=xlsread(‘shujv’,‘K1:K400’)
[NUMT]=xlsread(‘shujv’,‘A401:J538’)
[C]=xlsread(‘shujv’,‘K401:K538’)

mdl = ClassificationKNN.fit(NUM,A,‘NumNeighbors’,1);
predict_label = predict(mdl, NUMT);
accuracy = length(find(predict_label == C))/length©*100
測試分類標籤和預測分類標籤。(左側爲測試分類標籤,右側爲預測分類標籤)
在這裏插入圖片描述

實驗結果

正確率:正確率 = 預測標籤 / 測試標籤
accuracy = length(find(predict_label == C))/length©*100

在這裏插入圖片描述
由實驗結果可以看出來印度肝病患者這個數據集用BP網絡訓練的模型,分類的準確率更高。KNN自身的優點具有:計算簡單,易於理解,可解釋性強;比較適合處理有缺失屬性的樣本;能夠處理不相關的特徵;在相對短的時間內能夠對大型數據源做出可行且效果良好的結果。缺點是往往忽略了數據之間的相關性;BP神經網絡實質上實現了一個從輸入到輸出的映射功能,數學理論證明三層的神經網絡就能夠以任意精度逼近任何非線性連續函數。這使得其特別適合於求解內部機制複雜的問題,即BP神經網絡具有較強的非線性映射能力。BP神經網絡在其局部的或者部分的神經元受到破壞後對全局的訓練結果不會造成很大的影響,也就是說即使系統在受到局部損傷時還是可以正常工作的。即BP神經網絡具有一定的容錯能力。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章