案例算法 | 機器學習python應用,簡單機器學習項目實踐

​ 上一篇文章中介紹了機器學習的簡單知識,還有python中進行機器學習實踐需要的生態環境,接下來將會通過鳶尾花分類這個例子對機器學習做一個簡要的介紹。通過一步一步地實現這個項目來介紹以下內容。

  • 導入和使用python中機器學習的各個方面的類庫。
  • 導入數據,並通過描述性分析、可視化等對數據進行分析。
  • 創建六個模型,並從中選擇準確度最高的模型。

​ 可以說這並不是一個正式的項目,只是用來做一個簡單的展示,用於給初次接觸機器學習的讀者快速瞭解機器學習的過程和結果。

1 機器學習中的Hello World頂目

​ 學習編程時,往往我們的第一句代碼就是print(“Hello World”),而接下來的這個數據集,可以說得上是機器學習中的Hello World頂目,入門學習機器學習的過程中最常見的一個數據集。

​ 這個項目是針對鳶尾花(Iris Flower)進行分類的一個項目,數據集是含鳶尾花的三個亞屬的分類信息,通過機器學習算法生成一個模型,自動分類新數據到這三個亞屬的某一箇中。項目中使用的鳶尾花數據集是一個非常容易理解的數據集,這個數據集具有以下特點:

  • 所有的特徵數據都是數字,不需要考慮如何導入和處理數據 。
  • 這是一個分類問題,可以很方便地通過有監督學習算法來解決問題。
  • 這是一個多分類問題,也許需要一些特殊的處理。
  • 所有的特徵的數值採用相同的單位,不需要進行尺度的轉換 。
  • 三個類屬的數據完全一樣,沒有類別不平衡問題。
  • 有着較爲明顯的區分,機器學習分類效果較爲明顯。

​ 接下來我們將通過這個例子一步步地來展示一個機器學習項目的簡化步驟。我們將按照下面的步驟實現這個項目 :

(1)導入數據。

(2)概述數據。

(3)數據可視化。

(4)評估算法。

(5)實施預測。

​ 在整個項目的過程中,最好嘗試自己輸入每一行代碼,以加深對機器學習項目流程的理解。

2 導入數據

​ 導入項目所需的各種數據處理、數據可視化以及機器學習相關庫和鳶尾花(Iris Flower)數據集。

2.1 導入類庫

導入在項目中將要使用的類庫和方法 。 代碼如下 :

# 導入類庫
from pandas import read_csv
from pandas.plotting import scatter_matrix
import matplotlib.pyplot as plt
from sklearn.model_selection import train_test_split
from sklearn.model_selection import KFold
from sklearn.model_selection import cross_val_score
from sklearn.metrics import classification_report
from sklearn.metrics import confusion_matrix
from sklearn.metrics import accuracy_score
from sklearn.linear_model import LogisticRegression
from sklearn.tree import DecisionTreeClassifier
from sklearn.discriminant_analysis import LinearDiscriminantAnalysis
from sklearn.neighbors import KNeighborsClassifier
from sklearn.naive_bayes import GaussianNB
from sklearn.svm import SVC

​ 所有類庫的導入都不應有錯誤提示。如果出現了錯誤提示,那麼暫時停下來,先設置一個能夠運行的SciPy環境。

2.2 導入數據集

​ 在本項目中我們使用的是 UCI 機器學習數據倉庫中的鳶尾花(Iris Flower)數據集(http://archive.ics.uci.edu/rnl/datasets/Iris),不需要下載,可以通過sklearn模塊中datasets導入數據直接使用。在這裏將使用Pandas來導入數據和對數據進行描述性統計分析,並利用 Matplotlib實現數據可視化。需要注意的是,在導入數據時,爲每個數據特徵設定了名稱,這有助於後面對數據的展示工作,尤其是通過圖表展示數據。 代碼如下:

## 導入數據
import pandas as pd             # 導入pandas庫
from sklearn import datasets    # 導入sklearn模塊中的datasets,用以導入數據
iris = datasets.load_iris()     # 直接導入數據
dataset = pd.DataFrame(data=iris.data,columns=iris.feature_names)   # 用DataFrame存放數據

3 概述數據

​ 在導入數據之後,我們需要先看一下數據,增加對數據的理解,以便選擇合適的算法。我們將從以下幾個角度來審查數據:

(1)數據的維度。

(2)查看數據自身 。

(3)統計描述所有的數據特徵。

(4)數據分類的分佈情況。

​ 不要擔心這會需要很多代碼,每一種審查方法只有一行代碼。這些代碼非常有效,在以後的項目中也會用到。

3.1 數據維度

​ 通過查看數據的維度,可以對數據集有一個大概的瞭解,如數據集中有多少行數據、數據有幾個屬性等。代碼如下 :

#顯示數據維度
print('數據維度: 行 %s,列 %s' % dataset.shape)

​ 將會得到一個具有 150 行數據, 4 個數據特徵屬性的結果,執行結果如下:

數據維度: 行 150,列 4

3.2 查看數據自身

​ 查看數據自身也是一個很好的理解數據的方法,通過查看數據可以直觀地看到數據的特徵、數據的類型,以及大概的數據分佈範圍等。代碼如下:

# 查看數據的前10行
print(dataset.head(10))

​ 在這裏查看前10行記錄,執行結果如下:

   sepal length (cm)  sepal width (cm)  petal length (cm)  petal width (cm)
0                5.1               3.5                1.4               0.2
1                4.9               3.0                1.4               0.2
2                4.7               3.2                1.3               0.2
3                4.6               3.1                1.5               0.2
4                5.0               3.6                1.4               0.2
5                5.4               3.9                1.7               0.4
6                4.6               3.4                1.4               0.3
7                5.0               3.4                1.5               0.2
8                4.4               2.9                1.4               0.2
9                4.9               3.1                1.5               0.1

3.3 統計描述數據

​ 數據特徵的統計描述信息包括數據的行數、中位值、最大值、最小值、均值、四分位值等統計數據信息。我們需要通過這些統計的信息來大致瞭解數據的情況。配合箱線圖能夠很好了瞭解數據的分佈和數值大小還有異常值情況等,代碼如下:

# 統計描述數據信息
print(dataset.describe())

​ 執行結果如下:

       sepal length (cm)  sepal width (cm)  petal length (cm)  petal width (cm)  
count         150.000000        150.000000         150.000000        150.000000 
mean            5.843333          3.057333           3.758000          1.199333  
std             0.828066          0.435866           1.765298          0.762238 
min             4.300000          2.000000           1.000000          0.100000 
25%             5.100000          2.800000           1.600000          0.300000 
50%             5.800000          3.000000           4.350000          1.300000 
75%             6.400000          3.300000           5.100000          1.800000   
max             7.900000          4.400000           6.900000          2.500000

3.4 數據分類分佈

​ 接下來看一下數據在不同分類的分佈情況,執行程序後得到的將是每個分類數據量的絕對的數值,看一下各個分類的數據分佈是否均衡。代碼如下:

# 分類分佈情況
target = [x for x in iris.target]
for item in set(target):
    print("{} : {}".format(item,target.count(item)))

​ 這裏就是通過前面設定的數據特徵名稱來查看數據的 。 執行結果如下:

0 : 50
1 : 50
2 : 50

​ 我們可以看到鶯尾花的三個亞屬的數據各 50 條,分佈非常平衡。如果數據的分佈不平衡時,可能會影響到模型的準確度。因此,當數據分佈不平衡時,需要對數據進行處理,調整數據到相對平衡的狀態。調整數據平衡時有以下幾種方法。

  • 擴大數據樣本: 定向增加類別較少的數據,使其與其他類別達到一定的比列,但數據是非常珍貴的,通常情況下我們建模使用的數據就已經是全部的數據了,也無法再增加數據了。
  • 數據的重新抽樣:過抽樣 (複製少數類樣本)和欠抽樣(刪除多數類樣本)。當數據量很大時可以考慮測試欠抽樣,當數據量比較少時可以考慮過抽樣。
  • 生成人工樣本: 比如SMOTE方法,根據現有的數據,通過某些計算,生成更多的少類別的數據。
  • 異常檢測和變化檢測: 嘗試用不同的觀點進行思考,以解決問題。異常檢測是對罕見事件的檢測。這種思維的轉變在於考慮以小類作爲異常值類,它可以幫助獲得一種新方法來分離和分類樣本。

4 數據可視化

​ 通過對數據集的審查,對數據有了一個基本的瞭解,接下來將通過圖表來進一步查看數據特徵的分佈情況和數據不同特徵之間的相互關係 。

  • 使用單變量圖表可以更好地理解每一個特徵屬性。

  • 多變量圖表用於理解不同特徵屬性之間的關係。

    ​ 我們可以先看一下前面剛剛提到的分類分佈情況,執行代碼如下:

## 畫圖顯示
import matplotlib.pyplot as plt
%matplotlib inline
# 直方圖
plt.hist(target,[-0.5,0.5,1.5,2.5],rwidth=0.6)
plt.show()

類別情況

“C:\Users\CDA\Desktop\CDA\02 - SEO\01 - 原創\【算法應用】機器學習python應用-簡單機器學習項目實踐\圖片\類別情況.png”

​ 相對於數值而言,數據可視化後就非常直觀,我們可以清晰地瞭解到數據中的標籤類別個數以及每種類別間的大致比例情況。

4.1 單變量圖表

​ 單變量圖表可以顯示每一個單獨的特徵屬性,因爲每個特徵屬性都是數字,因此我們可以通過箱線圖來展示屬性與中位值的離散速度,瞭解數據偏向和異常值情況。 代碼如下:

# 箱線圖
dataset.plot(kind='box', subplots=True, layout=(2,2), sharex=False, sharey=False)
plt.show()

執行結果:

箱線圖

​ 還可以通過直方圖來顯示每個特徵屬性的分佈狀況。 代碼如下:

# 直方圖
dataset.hist()
plt.show()

​ 在輸出的圖表中,我們看到 separ- length 和 separ-width 這兩個特徵比較符合高斯分佈。執行結果如圖 3-2 所示 。

直方圖

4.2 多變量圖表

​ 通過多變量圖表可以查看不同特徵屬性之間的關係。我們通過散點矩陣圖來查看每個屬性之間的影響關係。

# 散點矩陣圖
import seaborn as sns                   # 導入畫圖庫-seaborn 
plt.figure(figsize=(15.0, 10.0))
sns.pairplot(dataset, diag_kind = 'kde', 
             plot_kws = {'alpha': 0.6, 's': 80, 'edgecolor': 'k'},
             size =3)
# 保存圖片
plt.savefig('scatter_matrix.jpg', dpi=100, bbox_inches='tight')

​ 執行結果如下所示,對角線上的四副圖是四個特徵的分佈情況,其意義和前面的直方圖內容的意義是一致的,很明顯看出 separ- length 和 separ-width 這兩個特徵是單峯的,比較符合高斯分佈;而 petal length 和 petal width是雙峯的。除了對角線外的其他圖則是散點圖的形式,它們表示的是不同特徵間的相關性,從圖中我們可以看出 petal length 和 petal width這兩個特徵間有着明顯的線性相關性。如果是迴歸模型中,出現多重共線性的特徵是需要進行處理的,但我們目前只是簡單的展示一下分類機器學習的大致流程,所以就沒必須做處理了。

散點矩陣圖

5 數據處理

​ 一般在機器學習的項目中,數據清洗、數據處理就佔去了整個項目的80%的工作量,所以這是機器學習項目中非常重要的一個環節,但在本項目中,iris的數據已經是非常完善的,不需要再進行過多的數據處理過程。如此我們只需要簡單處理一下原數據,使其更適合在某些有特殊要求的算法上使用。

5.1 數據標準化

​ 不同的算法對數據也有不同的要求,比如KNN算法,因爲一般是基於歐式距離進行計算,所以也要求數據必須要做標準化,否則建模過程中大小不一的特徵的實際權重也會不同,數值較大的特徵將會覆蓋掉數值較小的特徵。爲了解決這中影響,我們可以將數據標準化,執行代碼如下:

# 標準化處理
from sklearn import preprocessing
#建立StandardScaler對象
std = preprocessing.StandardScaler()
data_std = std.fit_transform(dataset)

5.2 分離出評估數據集

​ 模型被創建後需要知道創建的模型是否足夠好。在選擇算法的過程中會採用統計學方法來評估算法模型。但是,我們更想知道算法模型對真實數據的準確度如何,這就是保留一部分數據來評估算法模型的主要原因。下面將按照70%的訓練數據集,30%的評估數據集來分離數據。代碼如下:

# 分離數據集
## 原數據
X_train, X_validation, Y_train, Y_validation = train_test_split(dataset, target, test_size=0.3, random_state=12)
## 標準化數據
X_train_std, X_validation_std, Y_train, Y_validation = train_test_split(data_std, target, test_size=0.3, random_state=12)

​ 現在就分離出了 X_train 和 Y_train 或者標準化後的X_train_std和Y_train用來訓練算法創建模型, x_validation(X_validation_std)和Y_validation 在後面會用來驗證評估模型。

6 評估算法

​ 通過不同的算法來創建模型,並評估它們的準確度,以便找到最合適的算法。將按照下面的步驟進行操作:

(1)採用 10 折交叉驗證來評估算法模型 。

(2)生成幾個常用的分類模型來預測新數據 。

(3)選擇最優模型

6.1 評估模式

​ 在這裏將通過 10 折交叉驗證來分離訓練數據集,並評估算法模型的準確度。10 折交叉驗證是隨機地將數據分成 10 份,9 份用來訓練模型,1 份用來評估算法。後面我們會使用相同的數據對每一種算法進行訓練和評估 , 並從中選擇最好的模型。

6.2 創建模型

​ 對任何問題來說,不能僅通過對數據進行審查,就判斷出哪個算法最有效。通過前面的圖表,發現有些數據特徵符合線性分佈,所有可以期待算法會得到比較好的結果 。

接下來評估六種不同的算法:

  • 線性迴歸(LR)。
  • 神經網絡(ANN)
  • K 近鄰(KNN)。
  • 分類與迴歸樹(CART)。
  • 貝葉斯分類器(NB)。
  • 支持向量機(SVM)。

​ 這個算法列表中包含了線性算法(LR)和非線性算法(ANN、KNN 、CART、NB和SVM)。在每次對算法進行評估前都會重新設置隨機數的種子,以確保每次對算法的評估都使用相同的數據集,保證算法評估的準確性。接下來就創建並評估這六種算法模型。代碼如下:

# 算法審查
models = {}
models['LR'] = LogisticRegression()
models['ANN'] = MLPClassifier()
models['KNN'] = KNeighborsClassifier()
models['CART'] = DecisionTreeClassifier()
models['NB'] = GaussianNB()
models['SVM'] = SVC()

# 評估算法
results = []
for key in models:
    kfold = KFold(n_splits=10, random_state=seed)
    cv_results = cross_val_score(models[key], X_train, Y_train, cv=kfold, scoring='accuracy')
    results.append(cv_results)
    print('原數據:%s: %f (%f)' %(key, cv_results.mean(), cv_results.std()))

results = []
for key in models:
    kfold = KFold(n_splits=10, random_state=seed)
    cv_results = cross_val_score(models[key], X_train_std, Y_train, cv=kfold, scoring='accuracy')
    results.append(cv_results)
    print('標準化數據:%s: %f (%f)' %(key, cv_results.mean(), cv_results.std()))

6.3 選擇最優模型

​ 現在已經有了六種模型,並且評估了它們的精確度。接下來就需要比較這六種模型,並選出準確度最高的算法。執行上面的代碼,結果如下 :

原數據:LR: 0.933636 (0.062463)
原數據:ANN: 0.972727 (0.041660)
原數據:KNN: 0.972727 (0.041660)
原數據:CART: 0.914545 (0.066953)
原數據:NB: 0.933636 (0.062463)
原數據:SVM: 0.963636 (0.060302)

標準化數據:LR: 0.887273 (0.069734)
標準化數據:ANN: 0.942727 (0.064801)
標準化數據:KNN: 0.942727 (0.046895)
標準化數據:CART: 0.914545 (0.066953)
標準化數據:NB: 0.933636 (0.062463)
標準化數據:SVM: 0.951818 (0.065813)

​ 通過上面的結果,可以看出實際上用原數據進行建模的結果反而更好,說明這份數據不需要再更變動了。然後6種算法中神經網絡和KNN算法的準確率最高,這種情況下怎麼辦,該如何確定哪個纔是更好的。接下來創建一個箱線圖,通過圖表來比較算法的評估結果。 代碼如下 :

# 箱線圖比較算法
fig = plt.figure()
fig.suptitle('Algorithm Comparison')
ax = fig.add_subplot(111)
plt.boxplot(results)
ax.set_xticklabels(models.keys())
plt.show()

執行結果:

模型比較

​ 我們可以看出,雖然總體的平均準確率和標準差是一樣的,但是ANN算法的中值相對KNN的更高,說明ANN算法的相對來說會更好一點。

7 實施預測

​ 評估的結果顯示,神經網絡(ANN) 是準確度最高的算法。現在使用預留的評估數據集來驗證這個算法模型。這將會對生成的算法模型的準確度有一個更加直觀的認識。現在使用全部訓練集的數據生成神經網絡(ANN)的算法模型,並用預留的評估數據集給出一個算法模型的報告。 代碼如下:

#使用評估數據集評估算法
ann = MLPClassifier()
ann.fit(X=X_train, y=Y_train)
predictions = ann.predict(X_validation)
print("準確率:",accuracy_score(Y_validation, predictions))
print(confusion_matrix(Y_validation, predictions))
print(classification_report(Y_validation, predictions))

​ 執行程序後,看到算法模型的準確度是0.98。通過混淆矩陣看到只有一個數據預測錯誤。最後還提供了一個包含精確率(precision)、召回率(recall)、Fl 值(Fl-score)等數據的報告。結果如下:

準確率: 0.9777777777777777
[[20  0  0]
 [ 0 13  1]
 [ 0  0 11]]
              precision    recall  f1-score   support

           0       1.00      1.00      1.00        20
           1       1.00      0.93      0.96        14
           2       0.92      1.00      0.96        11

    accuracy                           0.98        45
   macro avg       0.97      0.98      0.97        45
weighted avg       0.98      0.98      0.98        45

8 總結

​ 到這裏已經完成了第一個機器學習項目。這個項目包含從數據導入到生成模型,以及通過模型對數據進行分類的全部過程。通過這個項目我們熟悉了機器學習項目中的各個步驟。接下來將介紹在本文中用到的對數據進行處理分析的技巧和算法,以及改進算法的實踐。

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