1. 程式人生 > >深度學習之路, 從邏輯迴歸開始, 手寫一個分類器.

深度學習之路, 從邏輯迴歸開始, 手寫一個分類器.

要給同事講神經網路和tensorflow. 需要普及一些前導知識.
所以我準備了一個課件, 寫了下面這個不使用工具和庫,全手寫的分類器. . 個人感覺, 對於幫助理解機器學習的具體實現過程是很有幫助的. (僅僅為了演示原理,實現寫的比較粗糙,談不上效能. )
放在這裡, 希望可以幫到其他同學.

宣告 : The MIT License
有需要的隨便拿去用.

import numpy as np
import matplotlib
import matplotlib.pyplot as plt
import math
import sys


dataset_raw = [
[0.051267
,0.69956,1 ], [-0.092742,0.68494,1 ], [-0.21371,0.69225,1 ], [-0.375,0.50219,1 ], [-0.51325,0.46564,1 ], [-0.52477,0.2098,1 ], [-0.39804,0.034357,1 ], [-0.30588,-0.19225,1 ], [0.016705,-0.40424,1 ], [0.13191,-0.51389,1 ], [0.38537,-0.56506,1 ], [0.52938,-0.5212,1 ], [0.63882,-0.24342,1 ], [0.73675,-0.18494,1 ], [0.54666,0.48757
,1 ], [0.322,0.5826,1 ], [0.16647,0.53874,1 ], [-0.046659,0.81652,1 ], [-0.17339,0.69956,1 ], [-0.47869,0.63377,1 ], [-0.60541,0.59722,1 ], [-0.62846,0.33406,1 ], [-0.59389,0.005117,1 ], [-0.42108,-0.27266,1 ], [-0.11578,-0.39693,1 ], [0.20104,-0.60161,1 ], [0.46601,-0.53582,1 ], [0.67339,-0.53582,1 ], [-0.13882,0.54605
,1 ], [-0.29435,0.77997,1 ], [-0.26555,0.96272,1 ], [-0.16187,0.8019,1 ], [-0.17339,0.64839,1 ], [-0.28283,0.47295,1 ], [-0.36348,0.31213,1 ], [-0.30012,0.027047,1 ], [-0.23675,-0.21418,1 ], [-0.06394,-0.18494,1 ], [0.062788,-0.16301,1 ], [0.22984,-0.41155,1 ], [0.2932,-0.2288,1 ], [0.48329,-0.18494,1 ], [0.64459,-0.14108,1 ], [0.46025,0.012427,1 ], [0.6273,0.15863,1 ], [0.57546,0.26827,1 ], [0.72523,0.44371,1 ], [0.22408,0.52412,1 ], [0.44297,0.67032,1 ], [0.322,0.69225,1 ], [0.13767,0.57529,1 ], [-0.0063364,0.39985,1 ], [-0.092742,0.55336,1 ], [-0.20795,0.35599,1 ], [-0.20795,0.17325,1 ], [-0.43836,0.21711,1 ], [-0.21947,-0.016813,1 ], [-0.13882,-0.27266,1 ], [0.18376,0.93348,0 ], [0.22408,0.77997,0 ], [0.29896,0.61915,0 ], [0.50634,0.75804,0 ], [0.61578,0.7288,0 ], [0.60426,0.59722,0 ], [0.76555,0.50219,0 ], [0.92684,0.3633,0 ], [0.82316,0.27558,0 ], [0.96141,0.085526,0 ], [0.93836,0.012427,0 ], [0.86348,-0.082602,0 ], [0.89804,-0.20687,0 ], [0.85196,-0.36769,0 ], [0.82892,-0.5212,0 ], [0.79435,-0.55775,0 ], [0.59274,-0.7405,0 ], [0.51786,-0.5943,0 ], [0.46601,-0.41886,0 ], [0.35081,-0.57968,0 ], [0.28744,-0.76974,0 ], [0.085829,-0.75512,0 ], [0.14919,-0.57968,0 ], [-0.13306,-0.4481,0 ], [-0.40956,-0.41155,0 ], [-0.39228,-0.25804,0 ], [-0.74366,-0.25804,0 ], [-0.69758,0.041667,0 ], [-0.75518,0.2902,0 ], [-0.69758,0.68494,0 ], [-0.4038,0.70687,0 ], [-0.38076,0.91886,0 ], [-0.50749,0.90424,0 ], [-0.54781,0.70687,0 ], [0.10311,0.77997,0 ], [0.057028,0.91886,0 ], [-0.10426,0.99196,0 ], [-0.081221,1.1089,0 ], [0.28744,1.087,0 ], [0.39689,0.82383,0 ], [0.63882,0.88962,0 ], [0.82316,0.66301,0 ], [0.67339,0.64108,0 ], [1.0709,0.10015,0 ], [-0.046659,-0.57968,0 ], [-0.23675,-0.63816,0 ], [-0.15035,-0.36769,0 ], [-0.49021,-0.3019,0 ], [-0.46717,-0.13377,0 ], [-0.28859,-0.060673,0 ], [-0.61118,-0.067982,0 ], [-0.66302,-0.21418,0 ], [-0.59965,-0.41886,0 ], [-0.72638,-0.082602,0 ], [-0.83007,0.31213,0 ], [-0.72062,0.53874,0 ], [-0.59389,0.49488,0 ], [-0.48445,0.99927,0 ], [-0.0063364,0.99927,0 ], [0.63265,-0.030612,0 ], ] dataset_np = np.array(dataset_raw) #feature engineering def prep_feature(x): x = np.insert(x, 2, np.power(x[:,0],2), axis=1) x = np.insert(x, 3, np.power(x[:,1],2), axis=1) x = np.insert(x, 4, np.multiply( x[:,0],x[:,1] ), axis=1) x = np.insert(x, 0, 1, axis=1) return x dataset_np = prep_feature(dataset_np) dataset_positive = dataset_np[ dataset_np[:,6] == 1 ] dataset_nagtive = dataset_np[ dataset_np[:,6] == 0 ] fig, ax = plt.subplots() ax.hold(True) ax.plot(dataset_positive[:,1], dataset_positive[:,2], 'o') ax.plot(dataset_nagtive[:,1], dataset_nagtive[:,2], 'x') #sys.exit() #extract the Y. dataset_y = dataset_np[:,6] #3 steps # define the model. theta = np.ones(6) learning_rate = 0.01 loss = [] def Sigmoid(z): # 1/(1+e^-z) s = np.frompyfunc(lambda x: 1/(1 + math.e**-z) , 1, 1) return s(z)[0] def Model(theta_,dataset_): # h(theta) theta' * dataset biased_dataset = dataset_.copy() #biased_dataset = np.insert(biased_dataset, 0, 1, axis=1) mt = np.matrix(biased_dataset)[:,:6].transpose() tt = np.matrix(theta) z = np.squeeze(np.asarray(tt * mt)) return Sigmoid(z),z def Cost(theta,predict,y): #J(theta) -y*log(h_theta(x)) - (1-y)log(1-h_theta(x)) part_1 = np.multiply(-y ,np.log( predict ) ) part_2 = np.multiply(1-y ,np.log( 1- predict )) total = np.subtract( part_1 , part_2) return np.sum(total) / len(y) / 2 #for test try: while True: theta_copy = theta.copy() predict_test,z = Model(theta_copy,dataset_np) cost_test = Cost(theta,predict_test,dataset_y) print(cost_test) loss.append(cost_test) for i in range(6): diff = np.subtract(predict_test , dataset_y) i_col_dataset = dataset_np[:,i] mt_diff = np.matrix(diff) mt_x = np.matrix(i_col_dataset).transpose() g = np.sum(mt_diff * mt_x) / len(dataset_np) * learning_rate #print("g(%d) is %f"%(i,g)) theta_copy[i] -= g theta = theta_copy except KeyboardInterrupt as e: print("stop traning...") # draw the decision bundry bundry_set = [] for i in range(200): for j in range(200): bundry_set.append([i/100-1,j/100 -1]) bundry_set_np = np.array(bundry_set) bundry_set_np_featured = prep_feature(bundry_set_np) predict_test,z = Model(theta,bundry_set_np_featured) dundry = bundry_set_np_featured[ np.logical_and( predict_test > 0.5 ,predict_test < 0.51 ) ] ax.plot(dundry[:,1], dundry[:,2], '.') print("end program...")

執行後自動開始訓練, 控制檯輸出loss, 當loss可以接受之後,按ctrl+c停止訓練.
稍等片刻, 可以看到程式影象輸出如下, 點為1, x為0, 綠色的圈是decision bundry.

這裡寫圖片描述