機器學習——決策樹(分類)

前言:內容參考周志華老師的《機器學習》,確實是一本好書,不過本科生讀懂仍是有很大難度的,大多數模型都是直接給出公式,其實本身私下有推導,涉及好多本身不懂的數學知識,會一點點補充的

機器學習專欄html

  1. 機器學習——線性迴歸(預測)
  2. 機器學習——邏輯迴歸(分類)
  3. 機器學習——特徵縮放
  4. 機器學習——正則化
  5. 機器學習——決策樹

1、決策樹基本流程

一顆決策樹(decision tree)包括根節點、若干內部節點和若干葉子節點,不斷的判斷->分支->再判斷->再分支……,決策樹的構成實際上是一個遞歸的過程,遵循分而治之的策略。
在這裏插入圖片描述
(圖源:周志華老師的《機器學習》)python

2、劃分選擇

決策樹,最重要的固然是決策(或者說叫選擇),那麼根據什麼標準進行選擇呢?如何劃分最優屬性?咱們但願決策樹的分支結點所包含的樣本儘量屬於同有類別,就是結點的「純度」(purity)愈來愈高。web

一、信息增益(ID3算法)

「信息熵」(information entropy)是度量樣本集合純度最經常使用的一種指標,信息熵的計算公式爲:
E n t ( D ) = k = 1 K p k l o g 2 p k Ent(D)=-\sum_{k=1}^{K}p_klog_2p_k
E n t ( D ) Ent(D) 的值越小,則 D D 的純度越高。其中, D D 是總樣本集, p k p_k 表示第 k k 類樣本出現的機率(第 k k 類樣本佔的比例), K K 是樣本總類數。

「信息增益」(information gain)表示知道一個屬性後,信息(標籤判斷)不肯定性減小的程度,信息增益的計算公式爲:
G a i n ( D , a ) = E n t ( D ) v = 1 V D v D E n t ( D v ) Gain(D,a)=Ent(D)-\sum_{v=1}^{V}\frac{|D^v|}{|D|}Ent(D^v)
其中,離散屬性 a a N N 種可能的取值 a 1 , a 2 , , a V {a^1,a^2,…,a^V} ,若是使用 a a 對樣本進行劃分,則會產生 V V 個分支結點,記 D v D^v D D 屬性 a a 上取值爲 a v a^v 的樣本集。
因此,「信息增益」越大,就意味着用屬性 a a 來劃分數據集 D D 來進行劃分所得到的純度提高越大。故著名的ID3決策樹算法就是以信息增益來選擇劃分屬性:
a = a r g      m a x a A    G a i n ( D , a ) a^*=\mathop{arg\;\;max}\limits_{a\in A}\; Gain(D,a) 算法

二、信息增益率(C4.5算法)

ID3決策樹經過信息增益選取劃分屬性,觀察信息增益的公式能夠看出,若是屬性 a a 的屬性值不少的狀況下,一個屬性值的分支節點的樣本純度就會很大,信息增益就會變大。因此C4.5決策算法採用「信息增益率」來選擇劃分屬性。
「信息增益率」定義:
G a i n _ r a t i o ( D , a ) = G a i n ( D , a ) I V ( a ) Gain\_ratio(D,a)=\frac{Gain(D,a)}{IV(a)}
其中
I V ( a ) = v = 1 V D v D l o g 2 D v D IV(a)=-\sum_{v=1}^{V}\frac{|D^v|}{|D|}log_2\frac{|D^v|}{|D|}
稱爲屬性 a a 的「固有值」(intrinsic value)。屬性 a a 的可能取值數目越多( V V 越大),則 I V ( a ) IV(a) 的值一般會越大。
可是,「信息增益率」準則可能會對取值數目較少的屬性有所偏好。因此,C4.5算法並非直接選擇「信息增益率」最大的候選劃分屬性,而是使用了一個啓發式算法:app

  1. 先從候選劃分屬性中找出信息增益高於平均水平的屬性;
  2. 再從中選擇信息增益率最高的。

三、基尼指數(CART算法)

CART決策樹使用「基尼指數」(Gini index)來選擇劃分屬性,數據集 D D 的純度用基尼指數來度量:
G i n i ( D ) = k = 1 K k k p k p k Gini(D)=\sum_{k=1}^{K}\sum_{k'\neq k}p_kp_{k'}
G i n i ( D ) Gini(D) 表示從 D D 中隨機抽取兩個樣本,其類別不同的機率,故 G i n i ( D ) Gini(D) 越小, D D 純度越高。
對屬性 a a 的基尼指數定義爲:
G i n i _ i n d e x ( D , a ) = v = 1 V D v D G i n i ( D v ) {Gini}\_{index(D,a)}=\sum_{v=1}^{V}\frac{D^v}{D}Gini(D^v)
所以,咱們選擇那個使劃分後基尼指數最小的屬性做爲最優劃分屬性,即:
a = a r g    m i n a A    G i n i _ i n d e x ( D , a ) a^*=\mathop {arg\;min}\limits_{a\in A}\;Gini\_index(D,a) 機器學習

3、剪枝處理

與線性迴歸同樣,決策樹也會存在過擬合的狀況,線性迴歸的過擬合主要是經過正則化實現(可參考個人另外一篇博客機器學習——特徵縮放、正則化),決策樹的過擬合主要是經過剪枝處理來避免的。ide

一、預剪枝

預剪枝是在決策樹生成的過程當中,對每一個結點進行劃分前先進行估計,若當前結點的劃分不能帶來決策樹泛化性能(驗證集的準確度)的提高,則中止劃分將當前結點做爲葉子結點(分類結果爲該結點下佔比大的類別)。
在這裏插入圖片描述
(圖源:周志華老師的《機器學習》)svg

二、後剪枝

後剪枝是指先從訓練集生成一顆完整的決策樹,而後自下而上對非葉子結點進行考察,若將該結點及其子結點替換爲葉子結點能夠提升泛化能力(驗證集的準確度),將該結點及其子結點替換爲葉子結點(分類結果爲該結點下佔比大的類別)。
在這裏插入圖片描述
(圖源:周志華老師的《機器學習》)性能

3、連續與缺失值處理

一、連續值處理

前面咱們討論的都是分類決策樹,主要是經過離散屬性來生成決策樹,現實問題中,咱們遇到的每每會有連續屬性,這時咱們就須要對連續值進行離散化處理,咱們一般採用二分法(C4.5中採用的方法)學習

二分法
給定樣本集D和連續屬性a,假定a在D中出現了n個不一樣的取值,將這些值從小到大進行排序,記爲 { a 1 , a 2 , a 3 , . . . , a n } \{a^1,a^2,a^3,...,a^n\} 。基於劃分點 t t 能夠將D分爲子集 D t D^-_t D t + D^+_t ,顯然對於相鄰的值 a i a i + 1 a^i和a^{i+1} 來講, t t 在區間 [ a i , a i + 1 ) [a^i,a^{i+1}) 中取任意值劃分結果是同樣的。所以,對於連續屬性a,可能的侯劃分點集合爲:
T a = a i + a i + 1 2 i [ 1 , n 1 ] T_a=\frac{a^i+a^{i+1}}{2}\quad i\in[1,n-1]
二分法就體如今這,即把區間 [ a i , a i + 1 ) [a^i,a^{i+1}) 的中位點 a i + a i + 1 2 \frac{a^i+a^{i+1}}{2} 做爲侯劃分點,咱們要選取最優的劃分點:
G a i n ( D , a ) = m a x t T a    G a i n ( D , a , t ) G a i n ( D , a , t ) = E n t ( D ) λ , + D t λ D E n t ( D t λ ) Gain(D,a)=\mathop {max}\limits_{t \in T_a}\;Gain(D,a,t)\\ Gain(D,a,t)=Ent(D)-\sum_{\lambda\in{-,+}}\frac{D_t^\lambda}{|D|}Ent(D_t^\lambda)
其中, G a i n ( D , a , t ) Gain(D,a,t) 就是樣本集D基於劃分點t二分後的信息增益,咱們就選擇使 G a i n ( D , a , t ) Gain(D,a,t) 最大化的劃分點。

二、缺失值處理

存在缺失值咱們主要有兩個問題:

  1. 如何在屬性值缺失的狀況下選擇最優劃分屬性(若有的樣本在「色澤」這個屬性上的值是缺失的,那麼該如何計算「色澤」的信息增益等?);
  2. 給定劃分屬性,若樣本在該屬性上缺失,如何對該樣本進行劃分(即這個樣本到底屬於哪一類?)。

對於問題1,現有數據集D和屬性a,令 D ~ \widetilde{D} 表示D在屬性a上沒有缺失值的樣本子集,咱們能夠根據 D ~ \widetilde{D} 來進行劃分屬性的選擇。現假定屬性a有V個值 a 1 , a 2 , . . . , a V {a^1,a^2,...,a^V} D ~ v \widetilde{D}^v 表示 D ~ \widetilde{D} 中屬性a取值爲 a v a^v 的樣本子集, D ~ k \widetilde{D}_k 表示 D ~ \widetilde{D} 中屬於第k類的樣本子集。則有:
{ D ~ = k = 1 K D ~ k D ~ = v = 1 V D ~ v \left\{\begin{matrix} \widetilde{D}=\bigcup_{k=1}^{K}\widetilde{D}_k\\ \widetilde{D}=\bigcup_{v=1}^{V}\widetilde{D}^v \end{matrix}\right.
初始,咱們爲每個樣本 x x 賦予一個權重 w x w_x (初始化爲1),並定義:
{ ρ = x D ~ w x x D w x p ~ k = x D ~ k w x x D ~ w x r ~ v = x D ~ v w x x D ~ w x \left\{\begin{matrix} \rho =\frac{\sum_{x\in \widetilde{D}}w_x}{\sum_{x\in D}w_x} \\ \widetilde{p}_k=\frac{\sum_{x \in \widetilde{D}_k}w_x}{\sum_{x \in \widetilde{D}}w_x} \\ \widetilde{r}_v=\frac{\sum_{x\in \widetilde{D}^v}w_x}{\sum_{x\in \widetilde{D}}w_x} \end{matrix}\right.
其中, ρ \rho 表示完好失值樣本所佔比例, p ~ k \widetilde{p}_k 表示完好失值樣本中第k類中所佔比例, r ~ v \widetilde{r}_v 表示完好失值樣本中在屬性a上取值爲v的樣本所佔比例。顯然:
{ k = 1 K p ~ k = 1 v = 1 V r ~ v = 1 \left\{\begin{matrix} \sum_{k=1}^{K}\widetilde{p}_k=1\\ \sum_{v=1}^{V}\widetilde{r}_v=1 \end{matrix}\right.
基於上述定義,咱們將含缺失值屬性的信息增益計算推廣爲:
G a i n ( D , a ) = ρ × G a i n ( D ~ , a ) = ρ × ( E n t ( D ~ ) v = 1 V r ~ v E n t ( D ~ v ) ) \begin{aligned} Gain(D,a)&=\rho \times Gain(\widetilde{D},a)\\ &=\rho \times (Ent(\widetilde{D})-\sum_{v=1}^{V}\widetilde{r}_vEnt(\widetilde{D}^v)) \end{aligned}
對問題2,若樣本 x x 在屬性a上的取值未知,則將 x x 劃入全部子結點,權值由 w x w_x 變爲 r ~ w x \widetilde{r}\cdot w_x ,即讓同一個樣本以不一樣的機率劃入不一樣的子結點中去。
這裏推薦一篇博客,講的很詳細(包括實例計算過程)決策樹(decision tree)(四)——缺失值處理

4、多變量決策樹

咱們把每一個屬性視爲座標空間中的一個座標軸,以前咱們介紹的單變量決策樹的分類邊界都是與各個座標軸平行
在這裏插入圖片描述
(圖源:周志華老師的《機器學習》)

可是,當學習任務的真實邊界比較複雜的時候,必需要使用不少段劃分才能得到較好的近似,此時生成的決策樹會很複雜。
此時,咱們可能須要斜邊去劃分,「多變量決策樹」(multivariate decision tree)的分葉子結點再也不是針對某一個屬性,而是一個線性分類器 i = 1 n w i a i = t \sum_{i=1}^{n}w_ia_i=t ,其中 w i w_i 是屬性 a i a_i 的權重, w i w_i 和t可在該結點所含的樣本集和屬性值上學的。
在這裏插入圖片描述

5、sklearn實現決策樹

能夠看一看這一篇博文:DecisionTreeClassifier重要參數
這裏再推薦一篇博文(分類結果的評價指標):分類效果評估

# -*- coding: utf-8 -*-
""" Created on Sun Nov 17 23:19:23 2019 @author: 1 """

from sklearn import tree
import pydotplus
from IPython.display import Image
import pandas as pd
from sklearn.model_selection import train_test_split
from sklearn.metrics import accuracy_score#準確率

df=pd.read_csv("D:\workspace\python\machine learning\data\iris.csv",sep=',')
iris_data=df.iloc[:,0:3]
iris_target=df.iloc[:,4]
iris_data_train,iris_data_test,iris_target_train,iris_target_test = train_test_split(iris_data,iris_target,train_size=.80)
clf = tree.DecisionTreeClassifier(criterion='gini')#criterion='gini'基尼指數,criterion='entropy'信息增益,
clf = clf.fit(iris_data_train, iris_target_train)  
dot_data = tree.export_graphviz(clf, out_file=None, 
                         feature_names=df.columns[:3], # 特徵名稱
                         class_names=df.columns[4], # 目標變量的類別
                         filled=True, rounded=True,  
                         special_characters=True)  
y_pred=clf.predict(iris_data_test)
print('accuracy_score:',accuracy_score(iris_target_test, y_pred))
graph = pydotplus.graph_from_dot_data(dot_data)  
image=Image(graph.create_png())

由iris數據集獲得的決策樹:
在這裏插入圖片描述

相關文章
相關標籤/搜索