分享一下 線性回歸中 欠擬合 和 過擬合 是怎么回事~
為了解決欠擬合的情 經常要提高線性的次數建立模型擬合曲線, 次數過高會導致過擬合,次數不夠會欠擬合。
再建立高次函數時候,要利用多項式特征生成器 生成訓練數據。
下面把整個流程展示一下
模擬了一個預測蛋糕價格的從欠擬合到過擬合的過程
git: https://github.com/linyi0604/MachineLearning
在做線性回歸預測時候,為了提高模型的泛化能力,經常采用多次線性函數建立模型
f = k*x + b 一次函數
f = a*x^2 + b*x + w 二次函數
f = a*x^3 + b*x^2 + c*x + w 三次函數
。。。
泛化:
對未訓練過的數據樣本進行預測。
欠擬合:
由於對訓練樣本的擬合程度不夠,導致模型的泛化能力不足。
過擬合:
訓練樣本擬合非常好,並且學習到了不希望學習到的特征,導致模型的泛化能力不足。
在建立超過一次函數的線性回歸模型之前,要對默認特征生成多項式特征再輸入給模型
poly2 = PolynomialFeatures(degree=2) # 2次多項式特征生成器
x_train_poly2 = poly2.fit_transform(x_train)
下面模擬 根據蛋糕的直徑大小 預測蛋糕價格
1 from sklearn.linear_model import LinearRegression 2 import numpy as np 3 import matplotlib.pyplot as plt 4 5 ''' 6 在做線性回歸預測時候, 7 為了提高模型的泛化能力,經常采用多次線性函數建立模型 8 9 f = k*x + b 一次函數 10 f = a*x^2 + b*x + w 二次函數 11 f = a*x^3 + b*x^2 + c*x + w 三次函數 12 。。。 13 14 泛化: 15 對未訓練過的數據樣本進行預測。 16 17 欠擬合: 18 由於對訓練樣本的擬合程度不夠,導致模型的泛化能力不足。 19 20 過擬合: 21 訓練樣本擬合非常好,並且學習到了不希望學習到的特征,導致模型的泛化能力不足。 22 23 24 在建立超過一次函數的線性回歸模型之前,要對默認特征生成多項式特征再輸入給模型 25 26 下面模擬 根據蛋糕的直徑大小 預測蛋糕價格 27 28 ''' 29 30 # 樣本的訓練數據,特征和目標值 31 x_train = [[6], [8], [10], [14], [18]] 32 y_train = [[7], [9], [13], [17.5], [18]] 33 34 # 一次線性回歸的學習與預測 35 # 線性回歸模型 學習 36 regressor = LinearRegression() 37 regressor.fit(x_train, y_train) 38 # 畫出一次線性回歸的擬合曲線 39 xx = np.linspace(0, 25, 100) # 0到16均勻采集100個點做x軸 40 xx = xx.reshape(xx.shape[0], 1) 41 yy = regressor.predict(xx) # 計算每個點對應的y 42 plt.scatter(x_train, y_train) # 畫出訓練數據的點 43 plt1, = plt.plot(xx, yy, label="degree=1") 44 plt.axis([0, 25, 0, 25]) 45 plt.xlabel("Diameter") 46 plt.ylabel("Price") 47 plt.legend(handles=[plt1]) 48 plt.show()
一次線性函數擬合曲線的結果,是欠擬合的情況:
下面進行建立2次線性回歸模型進行預測:
1 # 2次線性回歸進行預測 2 poly2 = PolynomialFeatures(degree=2) # 2次多項式特征生成器 3 x_train_poly2 = poly2.fit_transform(x_train) 4 # 建立模型預測 5 regressor_poly2 = LinearRegression() 6 regressor_poly2.fit(x_train_poly2, y_train) 7 # 畫出2次線性回歸的圖 8 xx_poly2 = poly2.transform(xx) 9 yy_poly2 = regressor_poly2.predict(xx_poly2) 10 plt.scatter(x_train, y_train) 11 plt1, = plt.plot(xx, yy, label="Degree1") 12 plt2, = plt.plot(xx, yy_poly2, label="Degree2") 13 plt.axis([0, 25, 0, 25]) 14 plt.xlabel("Diameter") 15 plt.ylabel("Price") 16 plt.legend(handles=[plt1, plt2]) 17 plt.show() 18 # 輸出二次回歸模型的預測樣本評分 19 print("二次線性模型在訓練數據上得分:", regressor_poly2.score(x_train_poly2, y_train)) # 0.9816421639597427
二次線性回歸模型擬合的曲線:
擬合程度明顯比1次線性擬合的要好
下面進行4次線性回歸模型:
1 # 進行四次線性回歸模型擬合 2 poly4 = PolynomialFeatures(degree=4) # 4次多項式特征生成器 3 x_train_poly4 = poly4.fit_transform(x_train) 4 # 建立模型預測 5 regressor_poly4 = LinearRegression() 6 regressor_poly4.fit(x_train_poly4, y_train) 7 # 畫出2次線性回歸的圖 8 xx_poly4 = poly4.transform(xx) 9 yy_poly4 = regressor_poly4.predict(xx_poly4) 10 plt.scatter(x_train, y_train) 11 plt1, = plt.plot(xx, yy, label="Degree1") 12 plt2, = plt.plot(xx, yy_poly2, label="Degree2") 13 plt4, = plt.plot(xx, yy_poly4, label="Degree2") 14 plt.axis([0, 25, 0, 25]) 15 plt.xlabel("Diameter") 16 plt.ylabel("Price") 17 plt.legend(handles=[plt1, plt2, plt4]) 18 plt.show() 19 # 輸出二次回歸模型的預測樣本評分 20 print("四次線性訓練數據上得分:", regressor_poly4.score(x_train_poly4, y_train)) # 1.0
四次線性模型預測准確率為百分之百, 但是看一下擬合曲線,明顯存在不合邏輯的預測曲線,
在樣本點之外的情況,可能預測的非常不准確,這種情況為過擬合
之前我們一直在展示在訓練集合上獲得的模型評分,次數越高的模型,訓練擬合越好。
下面查看一組測試數據進行預測的得分情況:
1 # 准備測試數據 2 x_test = [[6], [8], [11], [16]] 3 y_test = [[8], [12], [15], [18]] 4 print("一次線性模型在測試集合上得分:", regressor.score(x_test, y_test)) # 0.809726797707665 5 x_test_poly2 = poly2.transform(x_test) 6 print("二次線性模型在測試集合上得分:", regressor_poly2.score(x_test_poly2, y_test)) # 0.8675443656345054 7 x_test_poly4 = poly4.transform(x_test) 8 print("四次線性模型在測試集合上得分:", regressor_poly4.score(x_test_poly4, y_test)) # 0.8095880795746723
會發現,二次模型在預測集合上表現最好,四次模型表現反而不好!
這就是由於對訓練數據學習的太過分,學習到了不重要的東西,反而導致預測不准確。