sklearn中的分类决策树
決策樹
決策樹簡介
決策樹是一種使用if-then-else的決策規(guī)則的監(jiān)督學(xué)習(xí)方法.
其三要素為,枝節(jié)點(diǎn),葉節(jié)點(diǎn)與分支條件,同時為了減少過擬合還有剪枝方法
為了便于記憶,可以稱其為一方法三要素
決策樹的優(yōu)勢
- 便于理解和解釋。樹的結(jié)構(gòu)可以可視化出來。
- 訓(xùn)練需要的數(shù)據(jù)少。其他機(jī)器學(xué)習(xí)模型通常需要數(shù)據(jù)規(guī)范化,比如構(gòu)建虛擬變量和移除缺失值,不過請注意,這種模型不支持缺失值。
- 由于訓(xùn)練決策樹的數(shù)據(jù)點(diǎn)的數(shù)量導(dǎo)致了決策樹的使用開銷呈指數(shù)分布(訓(xùn)練樹模型的時間復(fù)雜度是參與訓(xùn)練數(shù)據(jù)點(diǎn)的對數(shù)值)。
- 能夠處理數(shù)值型數(shù)據(jù)和分類數(shù)據(jù)。其他的技術(shù)通常只能用來專門分析某一種變量類型的數(shù)據(jù)集。詳情請參閱算法。
- 能夠處理多路輸出的問題。
- 使用白盒模型。如果某種給定的情況在該模型中是可以觀察的,那么就可以輕易的通過布爾邏輯來解釋這種情況。相比之下,在黑盒模型中的結(jié)果就是很難說明清 楚地。
- 可以通過數(shù)值統(tǒng)計測試來驗(yàn)證該模型。這對事解釋驗(yàn)證該模型的可靠性成為可能。
- 即使該模型假設(shè)的結(jié)果與真實(shí)模型所提供的數(shù)據(jù)有些違反,其表現(xiàn)依舊良好。
決策樹的缺點(diǎn)
- 決策樹模型容易產(chǎn)生一個過于復(fù)雜的模型,這樣的模型對數(shù)據(jù)的泛化性能會很差。這就是所謂的過擬合.一些策略像剪枝、設(shè)置葉節(jié)點(diǎn)所需的最小樣本數(shù)或設(shè)置數(shù)的最大深度是避免出現(xiàn) 該問題最為有效地方法。
- 決策樹可能是不穩(wěn)定的,因?yàn)閿?shù)據(jù)中的微小變化可能會導(dǎo)致完全不同的樹生成。這個問題可以通過決策樹的集成來得到緩解
- 在多方面性能最優(yōu)和簡單化概念的要求下,學(xué)習(xí)一棵最優(yōu)決策樹通常是一個NP難問題。因此,實(shí)際的決策樹學(xué)習(xí)算法是基于啟發(fā)式算法,例如在每個節(jié)點(diǎn)進(jìn) 行局部最優(yōu)決策的貪心算法。這樣的算法不能保證返回全局最優(yōu)決策樹。這個問題可以通過集成學(xué)習(xí)來訓(xùn)練多棵決策樹來緩解,這多棵決策樹一般通過對特征和樣本有放回的隨機(jī)采樣來生成。
- 有些概念很難被決策樹學(xué)習(xí)到,因?yàn)闆Q策樹很難清楚的表述這些概念。例如XOR,奇偶或者復(fù)用器的問題。
- 如果某些類在問題中占主導(dǎo)地位會使得創(chuàng)建的決策樹有偏差。因此,我們建議在擬合前先對數(shù)據(jù)集進(jìn)行平衡。
分類
%matplotlib inline from sklearn import tree X = [[0, 0], [1, 1]] Y = [0, 1] clf = tree.DecisionTreeClassifier() clf = clf.fit(X, Y)predict the class of samples
print(clf.predict([[2,2]])) [1]show the probability and log_probability of each class be predicted
print(clf.predict_proba([[2,2]])) print(clf.predict_log_proba([[2,2]])) [[ 1. 0. 0.]] [[ 0. -inf -inf]]/home/fonttian/anaconda3/lib/python3.6/site-packages/sklearn/tree/tree.py:864: RuntimeWarning: divide by zero encountered in logreturn np.log(proba)在剛開始的時候我提出了三要素一方法,其中三要素不僅對應(yīng)著決策樹的構(gòu)成方式,還對應(yīng)著一方法也就是剪枝
決策樹因?yàn)槠鋵?shí)算法的特殊性,除非存在不同的兩個點(diǎn)或者以上在完全一致的特征下,分類標(biāo)簽不一致的情況,
決策樹可以做到對數(shù)據(jù)集的完全擬合.也正是決策樹的這一特性,使得完全的決策樹會產(chǎn)生嚴(yán)重的過擬合.
因此我們需要減掉過多的分支,從而提高決策樹的泛化能力.其中的方法雖然很多,但是整體而言都是圍繞著枝節(jié)點(diǎn)與葉節(jié)點(diǎn)展開的
在sklearn中我們可以用來提高決策樹泛化能力的超參數(shù)主要有
- max_depth:樹的最大深度,也就是說當(dāng)樹的深度到達(dá)max_depth的時候無論還有多少可以分支的特征,決策樹都會停止運(yùn)算.
- min_samples_split: 分裂所需的最小數(shù)量的節(jié)點(diǎn)數(shù).當(dāng)葉節(jié)點(diǎn)的樣本數(shù)量小于該參數(shù)后,則不再生成分支.該分支的標(biāo)簽分類以該分支下標(biāo)簽最多的類別為準(zhǔn)
- min_samples_leaf; 一個分支所需要的最少樣本數(shù),如果在分支之后,某一個新增葉節(jié)點(diǎn)的特征樣本數(shù)小于該超參數(shù),則退回,不再進(jìn)行剪枝.退回后的葉節(jié)點(diǎn)的標(biāo)簽以該葉節(jié)點(diǎn)中最多的標(biāo)簽?zāi)銥闇?zhǔn)
- min_weight_fraction_leaf: 最小的權(quán)重系數(shù)
- max_leaf_nodes:最大葉節(jié)點(diǎn)數(shù),None時無限制,取整數(shù)時,忽略max_depth
分支方式
對于決策樹而言,常見的決策樹分支方式一共有三種,前兩種是基于信息熵的,ID3(信息增益),C4.5(信息增益比),以及基于基尼系數(shù)的CART決策樹
但是因?yàn)榈侥壳盀橹?sklearn中只實(shí)現(xiàn)了ID3與CART決策樹,所以我們暫時只能使用這兩種決策樹,分支方式由超參數(shù)criterion決定:
- gini:默認(rèn)參數(shù),基于基尼系數(shù)
- entropy: 基于信息熵,也就是我們的ID3
* 下面在鳶尾花數(shù)據(jù)集上使用分類決策樹 *
* 加載數(shù)據(jù) *
from sklearn import datasets,model_selection def load_data():iris=datasets.load_iris() # scikit-learn 自帶的 iris 數(shù)據(jù)集X_train=iris.datay_train=iris.targetreturn model_selection.train_test_split(X_train, y_train,test_size=0.25,random_state=0,stratify=y_train)* 使用基尼(CART決策樹)與信息熵(ID3)進(jìn)行測試,可以發(fā)現(xiàn)在iris dataset上,gini的表現(xiàn)要好一些 *
* 同時可以發(fā)現(xiàn),對于決策樹而言,完全擬合數(shù)據(jù)并不困難,最多只需要 lg(n_samples)即可,對于iris的150個樣本而言,只需要max_depth就足夠了,但是max_depth的過度提高一般代表著泛化能力的降低 *
X_train,X_test,y_train,y_test=load_data() criterions=['gini','entropy'] for criterion in criterions:clf = DecisionTreeClassifier(criterion=criterion)clf.fit(X_train, y_train)print(criterion,"Training score:%f"%(clf.score(X_train,y_train)))print(criterion,"Testing score:%f"%(clf.score(X_test,y_test))) gini Training score:1.000000 gini Testing score:0.947368 entropy Training score:1.000000 entropy Testing score:0.947368* 下面是繪制的train_error 與test_error曲線,你也可容易通過修改其他幾個可以控制枝節(jié)點(diǎn)與葉節(jié)點(diǎn)的超參數(shù)對決策樹的生成進(jìn)行控制 *
maxdepth = 40X_train,X_test,y_train,y_test=load_data() depths=np.arange(1,maxdepth) training_scores=[] testing_scores=[] for depth in depths:clf = DecisionTreeClassifier(max_depth=depth)clf.fit(X_train, y_train)training_scores.append(clf.score(X_train,y_train))testing_scores.append(clf.score(X_test,y_test))## 繪圖 fig=plt.figure() ax=fig.add_subplot(1,1,1) ax.plot(depths,training_scores,label="traing score",marker='o') ax.plot(depths,testing_scores,label="testing score",marker='*') ax.set_xlabel("maxdepth") ax.set_ylabel("score") ax.set_title("Decision Tree Classification") ax.legend(framealpha=0.5,loc='best') plt.show()參考資料
- sklearn官方文檔:決策樹
總結(jié)
以上是生活随笔為你收集整理的sklearn中的分类决策树的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: auto-sklearn案例解析二
- 下一篇: 绘制决策树