1. 程式人生 > >清華AI自強計劃作業2實驗—邏輯迴歸模型

清華AI自強計劃作業2實驗—邏輯迴歸模型

問題:

執行模型輸出loss值為NAN,訓練200次後未出現線性模型
在這裡插入圖片描述

nan

nan的資料型別為float, not a number 的縮寫。python中判斷是否為nan型別的方法,使用math庫中的*isnan()*函式判斷:

from math import isnan
import numpy as np
res = np.nan
print (isnan(res))

無法確定運算結果時會返回nan結果.

回到問題本身:
bug出現在交叉熵損失函式的計算中:

sum_err -= Y[i]*np.log(Y_[i])+(1-Y[i])*np.log(1-Y_[i]

其中Y[i]為真值,Y_[i]為對應資料的預測值。
將np.log(Y_[i])打印出來發現型別為 -inf:負無窮大
發現在資料歸一化過程中,

Xmin = X.min(0)# 每列的最小值,輸出行為1列為2的陣列 # 通過使用 np.min 函式,計算原始資料沿著 axis=0 方向的最小值,即:求每一列的最小值,並賦值給 Xmin
Xmax = X.max(0)# 通過使用 np.max 函式,計算原始資料沿著 axis=0 方向的最大值,即:求每一列的最大值,並賦值給 Xmax
Xmu = np.mean(X)#

注意np.mean函式的用法:
np.mean(X,axis, out,keepdims)
axis為0,表示壓縮行,按列取均值,返回1n矩陣
axis為1,表示壓縮列,按行取均值,返回m

1矩陣
那麼在上述程式碼中,Xmu應當為np.mean(X,0),對各列取均值,下面的歸一化公式才可以計算正確:

X_norm = (X-Xmu)/(Xmax-Xmin)

修改Xmu = np.mean(X,0)後
顯示x_norm的值為:

在這裡插入圖片描述
原始資料繪圖:
可以看到橫軸縱軸的刻度全部依照真實資料

歸一化輸出結果是這樣的:

橫軸和縱軸均分別歸一化處理
擬合線性模型為:在這裡插入圖片描述

輸出損失值和準確值
Cost theta: [[ 0.48518509]]
Train Accuracy: 0.88

在批量梯度下降法中(Batch Gradient Descent,BGD),不斷更新權重 W

def BGD(X, y, iter_num, alpha):
trainMat = np.mat(X) # 通過使用 np.mat 函式,將資料集 X 轉換成矩陣型別,並賦值給 trainMat,trainMat的型別為ndarray,m3(在月薪和身高兩列之外,新增全為1的一列)
trainY = np.mat(y).T # 通過使用 np.mat 函式,將資料集 y 轉換成矩陣型別,並且轉置,然後賦值給 trainY
m, n = np.shape(X) # 通過使用 np.shape 函式,得到資料集 X 的形狀大小,其中,m 為資料集 X 的行數,n 為資料集 X 的列數
w = np.ones((n, 1)) # 通過使用 np.ones 函式,建立元素全為 1 的矩陣,矩陣的大小為 n 行 1 列,並賦值給 w, 即:進行權重 w 的初始化,令其全為 1
for i in range(iter_num): # 通過 for 迴圈結構,開始進行迭代,其中,i 可取的數依次為:0,1 ,2,…,iter_num-1, 迭代次數總共有 iter_num 次
error = sigmoid(trainMat

w)-trainY # 計算迭代的誤差 error:將預測得到的啟用函式的數值 sigmoid(trainMatw) 減去 實際的 trainY 數值
w = w-(1.0/m) * alpha
trainMat.Terror # 更新權重 w , BGD 批量梯度下降法 的核心, w = w - (1.0/m)alphatrainMat.Terror
return w # 返回 w’

sigmoid函式實現:

wx為m1矩陣,sigmoidV計算結果也為m1矩陣
def sigmoid(wx):
sigmoidV = 1.0/(1.0+np.exp(-wx))# 請補全
# 請補全 計算啟用函式 sigmoid 函式 的函式值,計算公式為:1.0/(1.0+np.exp(-wx))
return sigmoidV

iter_num為迭代次數,設m為資料行數
trainMat:m*3(第一列為1,第二列為身高標籤歸一化資料,第三列為月薪標籤歸一化資料)
w:3*1(初始化為全1矩陣,分別對應月薪引數、身高參數和偏置)
sigmoid函式返回矩陣:m*1
trainY:m*1
error :m*1 每組資料在此模型下的誤差
trainMat.T * error :3*1 ,和w的矩陣格式相同,因此可直接加減。

批量梯度下降法

每次使用所有樣本來進行函式的更新,
目標函式:
在這裡插入圖片描述
更新引數的方式:

在這裡插入圖片描述

程式碼中使用矩陣運算實現了公式中求和的功能, 和程式碼結合食用效果更佳!

ps:
根據課程群裡有同學提出的歸一化的問題,也親自做了實驗:
在當前資料下,減去均值和中位數進行歸一化是沒什麼區別的,cost值略有差別:

def normalization(X):
Xmin = X.min(0)# 每列的最小值,輸出行為1列為2的陣列 # 請補全 通過使用 np.min 函式,計算原始資料沿著 axis=0 方向的最小值,即:求每一列的最小值,並賦值給 Xmin
Xmax = X.max(0)# 通過使用 np.max 函式,計算原始資料沿著 axis=0 方向的最大值,即:求每一列的最大值,並賦值給 Xmax
Xmu = np.median(X,0)#通過使用 np.median函式求該列數值的中位數,計算原始資料均值,並賦值給 Xmu
X_norm = (X-Xmu)/(Xmax-Xmin)# 計算歸一化後的資料,歸一化公式為:(X-Xmu)/(Xmax-Xmin),歸一化後資料範圍為 [-1,1]
return X_norm # 返回資料預處理,歸一化後的資料 X_norm

在這裡插入圖片描述

Cost theta: [[ 0.48865864]]
Train Accuracy: 0.88

若減去最小值歸一化:
歸一化資料影象為:
在這裡插入圖片描述

線性模型:
在這裡插入圖片描述

Cost theta: [[ 0.57953747]]
Train Accuracy: 0.82

可見採用不同歸一化方法對模型訓練還是有不小影響的