【十】機器學習之路——logistic迴歸python實現
阿新 • • 發佈:2019-01-10
前面一個部落格機器學習之路——logistic迴歸講了logistic迴歸的理論知識,現在咱們來看一下logistic迴歸如何用python來實現,程式碼、資料參考《機器學習實戰》。
首先看下我們要處理的資料,
我們要做的就是通過logistic迴歸的方法,擬合一條曲線將紅色和綠色的點區分開來。話不多說,直接上程式碼,程式碼裡我已經儘可能的加了註釋,讓大家更容易看懂:
#!/usr/bin/env python
# -*- coding: utf-8 -*-
#上兩行程式碼作用是可以在註釋裡寫中文
import numpy as np
import matplotlib.pyplot as plt
#將測試資料匯入
def loadDataSet ():
dataMat = []; labelMat = []#dataMat為X輸入資料,labelMat為輸出0,1資料
fr = open('/Users/cailei/Cai_Lei/AI/MachineLearning_data/Ch05/testSet.txt')
for line in fr.readlines():
lineArr = line.strip().split()
#移除頭尾指定字元,並將資料分割為不同部分
dataMat.append([1.0,float(lineArr[0 ]),float(lineArr[1])])#令X0=1.0,X1為第一列資料,X2為第二列資料
labelMat.append(int(lineArr[2]))
#將第三列資料賦值為輸出資料
#print(dataMat)
return dataMat,labelMat
#定義Sigmond函式
def sigmoid (inX):
return 1.0/(1+np.exp(-inX))
#定義梯度上升函式
def gradAscent(dataMatIn,classLabels):
dataMatrix = np.mat(dataMatIn)#將X資料轉換為矩陣處理
labelMat = np.mat(classLabels).transpose()
#將輸出資料0,1轉換為矩陣並轉置
m,n=np.shape(dataMatIn)
#輸出dataMatIn矩陣維度,m=100行資料,n=3三列
alpha=0.01
maxCycle=500
weights=np.ones((n,1))
#定義w0,w1,w2初值為1,這裡用一個3*1的矩陣表示
for k in range(maxCycle):
h = sigmoid(dataMatrix*weights)
#這裡輸出X0,X1,X2代入到Sigmond的函式結果
error=labelMat-h #這裡計算(h(x)-y)*x裡的h(x)-y
weights=weights + alpha * dataMatrix.transpose()*error
#這裡進行w0,w1,w2權重的迭代計算,由於error是一個100*1列向量,dataMatrix是一個100*3的向量,因此相乘的話需要將dataMatrix進行轉置
print(weights)
return weights
#將擬合結果圖形和資料用plot函式顯示
def plotBestFit(weights):
dataMat,labelMat=loadDataSet()
dataArr = np.array(dataMat)
#將dataMat轉換為一個array,不懂的同學可以參考下面介紹的連結
n = np.shape(dataArr)[0]
#讀取第一維的長度,則shape函式後面加[0],其實我們知道共100組資料,這裡可以直接將n賦值100
xcord1 = []; ycord1 = []
xcord2 = []; ycord2 = []
#將資料分組,輸出為0的一組,輸出為1的一組
for i in range(n):
if int(labelMat[i])== 1:
xcord1.append(dataArr[i,1]); ycord1.append(dataArr[i,2])
else:
xcord2.append(dataArr[i,1]); ycord2.append(dataArr[i,2])
fig = plt.figure()
ax = fig.add_subplot(111)
ax.scatter(xcord1, ycord1, s=30, c='red', marker='s')
ax.scatter(xcord2, ycord2, s=30, c='green')
x = np.arange(-3.0, 3.0, 0.1)
y = (-weights[0]-weights[1]*x)/weights[2]
ax.plot(x, y)
plt.xlabel('X1'); plt.ylabel('X2');
plt.show()
def run():
dataArr,labelMat=loadDataSet()
weights=gradAscent(dataArr,labelMat)
plotBestFit(weights.getA())
if __name__ == '__main__':
run()
最終輸出的擬合曲線如下圖所示:
程式碼裡涉及到一些python的矩陣、陣列的處理等,初學python的同學可能會看的不太懂,append(),shape(),split()等一些函式的使用,網上有很多資源可以搜到,這裡不一一敘述。在寫程式碼的時候我也碰到了一些函式使用細節上的問題,打算下個部落格寫一個python裡矩陣陣列基本運算的一些函式的講解,盡請期待。