bp神經網絡及matlab實現


本文主要內容包含: (1) 介紹神經網絡基本原理,(2) AForge.NET實現前向神經網絡的方法,(3) Matlab實現前向神經網絡的方法 。


第0節、引例 

       本文以Fisher的Iris數據集作為神經網絡程序的測試數據集。Iris數據集能夠在http://en.wikipedia.org/wiki/Iris_flower_data_set  找到。這里簡要介紹一下Iris數據集:

有一批Iris花,已知這批Iris花可分為3個品種,現須要對其進行分類。不同品種的Iris花的花萼長度、花萼寬度、花瓣長度、花瓣寬度會有差異。我們現有一批已知品種的Iris花的花萼長度、花萼寬度、花瓣長度、花瓣寬度的數據。

  一種解決方法是用已有的數據訓練一個神經網絡用作分類器。

  假設你僅僅想用C#或Matlab高速實現神經網絡來解決你手頭上的問題,或者已經了解神經網絡基本原理,請直接跳到第二節——神經網絡實現。


第一節、神經網絡基本原理 

1. 人工神經元( Artificial Neuron )模型 

       人工神經元是神經網絡的基本元素,其原理能夠用下圖表示:

圖1. 人工神經元模型

 

       圖中x1~xn是從其它神經元傳來的輸入信號,wij表示表示從神經元j到神經元i的連接權值,θ表示一個閾值 ( threshold ),或稱為偏置( bias )。則神經元i的輸出與輸入的關系表示為:

 

  圖中 yi表示神經元i的輸出,函數f稱為激活函數 ( Activation Function )或轉移函數 ( Transfer Function ) ,net稱為凈激活(net activation)。若將閾值看成是神經元i的一個輸入x0的權重wi0,則上面的式子能夠簡化為:

 

  若用X表示輸入向量,用W表示權重向量,即:

X = [ x0 , x1 , x2 , ....... , xn ]

 

  則神經元的輸出能夠表示為向量相乘的形式:

 

 

       若神經元的凈激活net為正,稱該神經元處於激活狀態或興奮狀態(fire),若凈激活net為負,則稱神經元處於抑制狀態。

       圖1中的這樣的“閾值加權和”的神經元模型稱為M-P模型 ( McCulloch-Pitts Model ),也稱為神經網絡的一個處理單元( PE, Processing Element )


2. 經常使用激活函數 

       激活函數的選擇是構建神經網絡過程中的重要環節,以下簡要介紹經常使用的激活函數。

(1) 線性函數 ( Liner Function )

 

(2) 斜面函數 ( Ramp Function )

 

(3) 閾值函數 ( Threshold Function )

 


 

       以上3個激活函數都屬於線性函數,以下介紹兩個經常使用的非線性激活函數。

(4) S形函數 ( Sigmoid Function )

  該函數的導函數:

(5) 雙極S形函數 

  該函數的導函數:

  S形函數與雙極S形函數的圖像例如以下:


圖3. S形函數與雙極S形函數圖像

  雙極S形函數與S形函數主要差別在於函數的值域,雙極S形函數值域是(-1,1),而S形函數值域是(0,1)。

  因為S形函數與雙極S形函數都是可導的(導函數是連續函數),因此適合用在BP神經網絡中。(BP算法要求激活函數可導)


3. 神經網絡模型 

       神經網絡是由大量的神經元互聯而構成的網絡。依據網絡中神經元的互聯方式,常見網絡結構主要能夠分為以下3類:

(1) 前饋神經網絡 ( Feedforward Neural Networks )

       前饋網絡也稱前向網絡。這樣的網絡僅僅在訓練過程會有反饋信號,而在分類過程中數據僅僅能向前傳送,直到到達輸出層,層間沒有向后的反饋信號,因此被稱為前饋網絡。感知機( perceptron)與BP神經網絡就屬於前饋網絡。

       圖4 中是一個3層的前饋神經網絡,當中第一層是輸入單元,第二層稱為隱含層,第三層稱為輸出層(輸入單元不是神經元,因此圖中有2層神經元)。

圖4. 前饋神經網絡

 

  對於一個3層的前饋神經網絡N,若用X表示網絡的輸入向量,W1~W3表示網絡各層的連接權向量,F1~F3表示神經網絡3層的激活函數。

  那么神經網絡的第一層神經元的輸出為:

O1 = F1( XW1 )

  第二層的輸出為:

O2 = F2 ( F1( XW1 ) W2 )

  輸出層的輸出為:

O3 = F3( F2 ( F1( XW1 ) W2 ) W3 )

       若激活函數F1~F3都選用線性函數,那么神經網絡的輸出O3將是輸入X的線性函數。因此,若要做高次函數的逼近就應該選用適當的非線性函數作為激活函數。

(2) 反饋神經網絡 ( Feedback Neural Networks )

       反饋型神經網絡是一種從輸出到輸入具有反饋連接的神經網絡,其結構比前饋網絡要復雜得多。典型的反饋型神經網絡有:Elman網絡和Hopfield網絡。

圖5. 反饋神經網絡

 

(3) 自組織網絡 ( SOM ,Self-Organizing Neural Networks )

       自組織神經網絡是一種無導師學習網絡。它通過自己主動尋找樣本中的內在規律和本質屬性,自組織、自適應地改變網絡參數與結構。

圖6. 自組織網絡

 

4. 神經網絡工作方式 

       神經網絡運作過程分為學習和工作兩種狀態。

(1)神經網絡的學習狀態 

       網絡的學習主要是指使用學習算法來調整神經元間的聯接權,使得網絡輸出更符合實際。學習算法分為有導師學習( Supervised Learning )無導師學習( Unsupervised Learning )兩類。

       有導師學習算法將一組訓練集 ( training set )送入網絡,依據網絡的實際輸出與期望輸出間的區別來調整連接權。有導師學習算法的主要步驟包含:

1)  從樣本集合中取一個樣本(Ai,Bi);

2)  計算網絡的實際輸出O;

3)  求D=Bi-O;

4)  依據D調整權矩陣W;

5) 對每一個樣本反復上述過程,直到對整個樣本集來說,誤差不超過規定范圍。

  BP算法就是一種出色的有導師學習算法。

       無導師學習抽取樣本集合中蘊含的統計特性,並以神經元之間的聯接權的形式存於網絡中。

       Hebb學習律是一種經典的無導師學習算法。

(2) 神經網絡的工作狀態 

       神經元間的連接權不變,神經網絡作為分類器、預測器等使用。

  以下簡要介紹一下Hebb學習率與Delta學習規則 。

(3) 無導師學習算法:Hebb學習率 

  Hebb算法核心思想是,當兩個神經元同一時候處於激發狀態時兩者間的連接權會被加強,否則被減弱。 

       為了理解Hebb算法,有必要簡介一下條件反射實驗。巴甫洛夫的條件反射實驗:每次給狗喂食前都先響鈴,時間一長,狗就會將鈴聲和食物聯系起來。以后假設響鈴可是不給食物,狗也會流口水。

圖7. 巴甫洛夫的條件反射實驗

 

  受該實驗的啟示,Hebb的理論覺得在同一時間被激發的神經元間的聯系會被強化。比方,鈴聲響時一個神經元被激發,在同一時間食物的出現會激發附近的還有一個神經元,那么這兩個神經元間的聯系就會強化,從而記住這兩個事物之間存在着聯系。相反,假設兩個神經元總是不能同步激發,那么它們間的聯系將會越來越弱。

  Hebb學習律可表示為:

       當中wij表示神經元j到神經元i的連接權,yi與yj為兩個神經元的輸出,a是表示學習速度的常數。若yi與yj同一時候被激活,即yi與yj同一時候為正,那么Wij將增大。若yi被激活,而yj處於抑制狀態,即yi為正yj為負,那么Wij將變小。

(4) 有導師學習算法:Delta學習規則

  Delta學習規則是一種簡單的有導師學習算法,該算法依據神經元的實際輸出與期望輸出區別來調整連接權,其數學表演示樣例如以下:

 

       當中Wij表示神經元j到神經元i的連接權,di是神經元i的期望輸出,yi是神經元i的實際輸出,xj表示神經元j狀態,若神經元j處於激活態則xj為1,若處於抑制狀態則xj為0或-1(依據激活函數而定)。a是表示學習速度的常數。如果xi為1,若di比yi大,那么Wij將增大,若di比yi小,那么Wij將變小。

       Delta規則簡單講來就是:若神經元實際輸出比期望輸出大,則減小全部輸入為正的連接的權重,增大全部輸入為負的連接的權重。反之,若神經元實際輸出比期望輸出小,則增大全部輸入為正的連接的權重,減小全部輸入為負的連接的權重。這個增大或減小的幅度就依據上面的式子來計算。

(5)有導師學習算法:BP算法 

  採用BP學習算法的前饋型神經網絡通常被稱為BP網絡。

圖8. 三層BP神經網絡結構

 

  BP網絡具有非常強的非線性映射能力,一個3層BP神經網絡可以實現對隨意非線性函數進行逼近(依據Kolrnogorov定理)。一個典型的3層BP神經網絡模型如圖7所看到的。

  BP網絡的學習算法占篇幅較大,我打算在下一篇文章中介紹。

 

第二節、神經網絡實現 

 

1. 數據預處理 

       在訓練神經網絡前一般須要對數據進行預處理,一種重要的預處理手段是歸一化處理。以下簡要介紹歸一化處理的原理與方法。

(1) 什么是歸一化? 

數據歸一化,就是將數據映射到[0,1]或[-1,1]區間或更小的區間,比方(0.1,0.9) 。

(2) 為什么要歸一化處理? 

<1>輸入數據的單位不一樣,有些數據的范圍可能特別大,導致的結果是神經網絡收斂慢、訓練時間長。

<2>數據范圍大的輸入在模式分類中的作用可能會偏大,而數據范圍小的輸入作用就可能會偏小。

<3>因為神經網絡輸出層的激活函數的值域是有限制的,因此須要將網絡訓練的目標數據映射到激活函數的值域。比如神經網絡的輸出層若採用S形激活函數,因為S形函數的值域限制在(0,1),也就是說神經網絡的輸出僅僅能限制在(0,1),所以訓練數據的輸出就要歸一化到[0,1]區間。

<4>S形激活函數在(0,1)區間以外區域非常平緩,區分度太小。比如S形函數f(X)在參數a=1時,f(100)與f(5)僅僅相差0.0067。

(3) 歸一化算法 

  一種簡單而高速的歸一化算法是線性轉換算法。線性轉換算法常見有兩種形式:

       <1>

y = ( x - min )/( max - min )

  當中min為x的最小值,max為x的最大值,輸入向量為x,歸一化后的輸出向量為y 。上式將數據歸一化到 [ 0 , 1 ]區間,當激活函數採用S形函數時(值域為(0,1))時這條式子適用。

       <2>

y = 2 * ( x - min ) / ( max - min ) - 1

       這條公式將數據歸一化到 [ -1 , 1 ] 區間。當激活函數採用雙極S形函數(值域為(-1,1))時這條式子適用。

(4) Matlab數據歸一化處理函數 

  Matlab中歸一化處理數據能夠採用premnmx , postmnmx , tramnmx 這3個函數。

<1> premnmx

語法:[pn,minp,maxp,tn,mint,maxt] = premnmx(p,t)

參數:

pn: p矩陣按行歸一化后的矩陣

minp,maxp:p矩陣每一行的最小值,最大值

tn:t矩陣按行歸一化后的矩陣

mint,maxt:t矩陣每一行的最小值,最大值

作用:將矩陣p,t歸一化到[-1,1] ,主要用於歸一化處理訓練數據集。

<2> tramnmx

語法:[pn] = tramnmx(p,minp,maxp)

參數:

minp,maxp:premnmx函數計算的矩陣的最小,最大值

pn:歸一化后的矩陣

作用:主要用於歸一化處理待分類的輸入數據。

<3> postmnmx

語法: [p,t] = postmnmx(pn,minp,maxp,tn,mint,maxt)

參數:

minp,maxp:premnmx函數計算的p矩陣每行的最小值,最大值

mint,maxt:premnmx函數計算的t矩陣每行的最小值,最大值

作用:將矩陣pn,tn映射回歸一化處理前的范圍。postmnmx函數主要用於將神經網絡的輸出結果映射回歸一化前的數據范圍。

2. 使用Matlab實現神經網絡 

使用Matlab建立前饋神經網絡主要會使用到以下3個函數:

newff :前饋網絡創建函數

train:訓練一個神經網絡

sim :使用網絡進行仿真

 以下簡要介紹這3個函數的使用方法。

(1) newff函數

<1>newff函數語法 

       newff函數參數列表有非常多的可選參數,詳細能夠參考Matlab的幫助文檔,這里介紹newff函數的一種簡單的形式。

語法:net = newff ( A, B, {C} ,‘trainFun’)

參數:

A:一個n×2的矩陣,第i行元素為輸入信號xi的最小值和最大值;

B:一個k維行向量,其元素為網絡中各層節點數;

C:一個k維字符串行向量,每一分量為相應層神經元的激活函數

trainFun :為學習規則採用的訓練算法

<2>經常使用的激活函數

  經常使用的激活函數有:

  a) 線性函數 (Linear transfer function)

f(x) = x

  該函數的字符串為’purelin’。

 

b) 對數S形轉移函數( Logarithmic sigmoid transfer function )

    該函數的字符串為’logsig’。

c) 雙曲正切S形函數 (Hyperbolic tangent sigmoid transfer function )

  也就是上面所提到的雙極S形函數。

 

  該函數的字符串為’ tansig’。

  Matlab的安裝文件夾下的toolbox\nnet\nnet\nntransfer子文件夾中有全部激活函數的定義說明。

<3>常見的訓練函數

    常見的訓練函數有:

traingd :梯度下降BP訓練函數(Gradient descent backpropagation)

traingdx :梯度下降自適應學習率訓練函數

<4>網絡配置參數

一些重要的網絡配置參數例如以下:

net.trainparam.goal  :神經網絡訓練的目標誤差

net.trainparam.show   : 顯示中間結果的周期

net.trainparam.epochs  :最大迭代次數

net.trainParam.lr    : 學習率

(2) train函數

    網絡訓練學習函數。

語法:[ net, tr, Y1, E ]  = train( net, X, Y )

參數:

X:網絡實際輸入

Y:網絡應有輸出

tr:訓練跟蹤信息

Y1:網絡實際輸出

E:誤差矩陣

(3) sim函數

語法:Y=sim(net,X)

參數:

net:網絡

X:輸入給網絡的K×N矩陣,當中K為網絡輸入個數,N為數據樣本數

Y:輸出矩陣Q×N,當中Q為網絡輸出個數

(4) Matlab BP網絡實例 

       我將Iris數據集分為2組,每組各75個樣本,每組中每種花各有25個樣本。當中一組作為以上程序的訓練樣本,另外一組作為檢驗樣本。為了方便訓練,將3類花分別編號為1,2,3 。

  使用這些數據訓練一個4輸入(分別相應4個特征),3輸出(分別相應該樣本屬於某一品種的可能性大小)的前向網絡。

       Matlab程序例如以下:

復制代碼
   
   
  
  
          
% 讀取訓練數據 [f1,f2,f3,f4,class] = textread( ' trainData.txt ' , ' %f%f%f%f%f ' , 150 ); % 特征值歸一化 [input,minI,maxI] = premnmx( [f1 , f2 , f3 , f4 ] ' ) ; % 構造輸出矩陣 s = length( class ) ; output = zeros( s , 3 ) ; for i = 1 : s output( i , class( i ) ) = 1 ; end % 創建神經網絡 net = newff( minmax(input) , [ 10 3 ] , { ' logsig ' ' purelin ' } , ' traingdx ' ) ; % 設置訓練參數 net.trainparam.show = 50 ; net.trainparam.epochs = 500 ; net.trainparam.goal = 0.01 ; net.trainParam.lr = 0.01 ; % 開始訓練 net = train( net, input , output ' ) ; % 讀取測試數據 [t1 t2 t3 t4 c] = textread( ' testData.txt ' , ' %f%f%f%f%f ' , 150 ); % 測試數據歸一化 testInput = tramnmx ( [t1,t2,t3,t4] ' , minI, maxI ) ; % 仿真 Y = sim( net , testInput ) % 統計識別正確率 [s1 , s2] = size( Y ) ; hitNum = 0 ; for i = 1 : s2 [m , Index] = max( Y( : , i ) ) ; if ( Index == c(i) ) hitNum = hitNum + 1 ; end end sprintf( ' 識別率是 %3.3f%% ' , 100 * hitNum / s2 )
復制代碼


  以上程序的識別率穩定在95%左右,訓練100次左右達到收斂,訓練曲線例如以下圖所看到的:

圖9. 訓練性能表現

 

(5)參數設置對神經網絡性能的影響 

       我在實驗中通過調整隱含層節點數,選擇不通過的激活函數,設定不同的學習率,

 

<1>隱含層節點個數 

  隱含層節點的個數對於識別率的影響並不大,可是節點個數過多會添加運算量,使得訓練較慢。

 

<2>激活函數的選擇 

       激活函數不管對於識別率或收斂速度都有顯著的影響。在逼近高次曲線時,S形函數精度比線性函數要高得多,但計算量也要大得多。

 

<3>學習率的選擇 

       學習率影響着網絡收斂的速度,以及網絡是否能收斂。學習率設置偏小能夠保證網絡收斂,可是收斂較慢。相反,學習率設置偏大則有可能使網絡訓練不收斂,影響識別效果。

 

3. 使用AForge.NET實現神經網絡 

(1) AForge.NET簡單介紹 

       AForge.NET是一個C#實現的面向人工智能、計算機視覺等領域的開源架構。AForge.NET源碼下的Neuro文件夾包括一個神經網絡的類庫。

AForge.NET主頁:http://www.aforgenet.com/

AForge.NET代碼下載:http://code.google.com/p/aforge/

Aforge.Neuroproject的類圖例如以下:

 

圖10. AForge.Neuro類庫類圖

 

以下介紹圖9中的幾個主要的類:

Neuron — 神經元的抽象基類

Layer — 層的抽象基類,由多個神經元組成

Network —神經網絡的抽象基類,由多個層(Layer)組成

IActivationFunction - 激活函數(activation function)的接口

IUnsupervisedLearning - 無導師學習(unsupervised learning)算法的接口ISupervisedLearning - 有導師學習(supervised learning)算法的接口

 

(2)使用Aforge建立BP神經網絡 

       使用AForge建立BP神經網絡會用到以下的幾個類:

<1>  SigmoidFunction : S形神經網絡

  構造函數:public SigmoidFunction( double alpha )

   參數alpha決定S形函數的陡峭程度。

<2>  ActivationNetwork :神經網絡類

  構造函數:

  public ActivationNetwork( IActivationFunction function, int inputsCount, params int[] neuronsCount )

                         : base( inputsCount, neuronsCount.Length )

  public virtual double[] Compute( double[] input )

 

參數意義:

inputsCount:輸入個數

neuronsCount :表示各層神經元個數

<3>  BackPropagationLearning:BP學習算法

 構造函數:

public BackPropagationLearning( ActivationNetwork network )

 參數意義:

network :要訓練的神經網絡對象

BackPropagationLearning類須要用戶設置的屬性有以下2個:

learningRate :學習率

momentum :沖量因子

以下給出一個用AForge構建BP網絡的代碼。

 

復制代碼
    
    
   
   
           
// 創建一個多層神經網絡,採用S形激活函數,各層分別有4,5,3個神經元
//(當中4是輸入個數,3是輸出個數,5是中間層結點個數) ActivationNetwork network = new ActivationNetwork( new SigmoidFunction(2), 4, 5, 3); // 創建訓練算法對象 BackPropagationLearning teacher = new BackPropagationLearning(network); // 設置BP算法的學習率與沖量系數 teacher.LearningRate = 0.1; teacher.Momentum = 0; int iteration = 1 ; // 迭代訓練500次 while( iteration < 500 ) { teacher.RunEpoch( trainInput , trainOutput ) ; ++iteration ; } //使用訓練出來的神經網絡來分類,t為輸入數據向量 network.Compute(t)[0]
復制代碼

 

       改程序對Iris 數據進行分類,識別率可達97%左右 。


     點擊下載源碼


  文章來自:http://www.cnblogs.com/heaad/  

 轉載:http://www.cnblogs.com/heaad/archive/2011/03/07/1976443.html


免責聲明!

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



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