import os
os.chdir('E:/ML/machine-learning-ex2')
print('现在工作目录是 '+str(os.getcwd()))
#可视化数据
import pandas as pd
import matplotlib.pyplot as plt
import numpy as np
ex2data1=pd.read_csv('ex2data1.txt',names=['exam1','exam2','admitted'])
ex2data1.insert(0,'intercept',np.ones(ex2data1.shape[0]))#增加常数项
X=ex2data1.iloc[:,0:3];y=ex2data1.iloc[:,3:]#若写成y=ex2data1.iloc[:,3],会出现维数问题
#按y值划分数据集
pos=(ex2data1.iloc[:,-1]==1);neg=(ex2data1.iloc[:,-1]==0)
X_pos=np.mat(X[pos]);X_neg=np.mat(X[neg])
fig,ax=plt.subplots()
ax.scatter(X_pos[:,1].flat,X_pos[:,2].flat,marker='x',label='Admitted')
ax.scatter(X_neg[:,1].flat,X_neg[:,2].flat,marker='o',label='Not Admitted')
ax.legend(loc='upper right')
ax.set_xlabel('exam1')
ax.set_ylabel('exam2')
plt.show()
#定义逻辑函数和代价函数;
def sigmoid(z):
g=1/(1+np.exp(-z))
return g
def computeCost(theta,X,y):
#代价函数同时返回代价和梯度;
m=len(y)
X=np.mat(X);y=np.mat(y).reshape(X.shape[0],1);theta=np.mat(theta).reshape(X.shape[1],1)
h=sigmoid(X*theta)
cost=-1/m*(y.T*np.log(h)+(1-y).T*np.log(1-h))
grad=1/m*X.T*(h-y)
return cost,grad
#定义梯度下降函数------最原始版本
def gradientDescent(theta,X,y,alpha,iterations):
#原始梯度下降函数,返回最佳theta值和每次循环的代价值列表J,列表J可用来判断函数执行情况是否理想
#会报错:RuntimeWarning: divide by zero encountered in log
J=np.zeros((iterations,1))
for i in range(iterations):
cost,grad=computeCost(theta,X,y)
theta=theta-alpha*grad
J[i]=cost
return theta,J
#执行梯度下降
theta=np.zeros((X.shape[1],1)) #设置初始theta
theta,J=gradientDescent(theta,X,y,0.1,5000)
会报错:RuntimeWarning: divide by zero encountered in log
主要原因是原始数据计算量大。
一个方法是对原始数据进行均值标准化;另一个是用高级梯度下降方法。
#解决方法一:对数据X进行均值标准化,可以减少计算量;
#解决方法二:运用高级梯度下降算法:scipy.optimize.fmin_tnc
#解决方法一:对数据X进行均值标准化,可以减少计算量;
#特征标准化
mean_X=np.mean(X);mean_X.iloc[0]=0
range_X=np.max(X)-np.min(X);range_X.iloc[0]=1 #常数项保持不变,均值定为0,范围定为1;
normal_X=(X-mean_X)/range_X
#定义梯度下降函数------最原始版本
def gradientDescent(theta,X,y,alpha,iterations):
#原始梯度下降函数,返回最佳theta值和每次循环的代价值列表J,列表J可用来判断函数执行情况是否理想
J=np.zeros((iterations,1))
for i in range(iterations):
cost,grad=computeCost(theta,X,y)
theta=theta-alpha*grad
J[i]=cost
return theta,J
#执行梯度下降
theta=np.zeros((X.shape[1],1)) #设置初始theta
theta,J=gradientDescent(theta,normal_X,y,0.1,5000) #此处的最佳theta值匹配的是标准后的数据normal_X;
print('best of theta is:'+str(theta))
fig,axs=plt.subplots(2,1)
axs[0].plot(J)
axs[0].set_ylabel('J')
#画出决策边界
normal_X_pos=np.mat(normal_X[pos]);normal_X_neg=np.mat(normal_X[neg])
axs[1].scatter(normal_X_pos[:,1].flat,normal_X_pos[:,2].flat,marker='x',label='Admitted')
axs[1].scatter(normal_X_neg[:,1].flat,normal_X_neg[:,2].flat,marker='o',label='Not Admitted')
axs[1].legend(loc='upper right')
axs[1].set_xlabel('exam1')
axs[1].set_ylabel('exam2')
X1=np.linspace(-0.5,0.5,30)
intercept=np.ones((30))
X2=(-intercept*theta[0,0]-X1*theta[1,0])/theta[2,0]
axs[1].plot(X1,X2)
plt.show()
#解决方法二:运用高级梯度下降算法:scipy.optimize.fmin_tnc
import scipy.optimize as opt
X=np.mat(X);y=np.mat(y)
theta=np.zeros((X.shape[1],1))
theta=np.mat(theta)
result=opt.fmin_tnc(func=computeCost,x0=theta,args=(X,y))
theta=result[0].reshape(theta.shape) #此处的最佳theta值匹配的是原始数据X;
#画出决策边界
plt.scatter(X_pos[:,1].flat,X_pos[:,2].flat,marker='x',label='pos')
plt.scatter(X_neg[:,1].flat,X_neg[:,2].flat,marker='o',label='neg')
plt.legend(loc='upper right')
X1=np.linspace(25,100,30)
intercept=np.ones((30))
X2=(-intercept*theta[0,0]-X1*theta[1,0])/theta[2,0]
plt.plot(X1,X2)
plt.show()
吴恩达机器学习编程作业
链接: https://pan.baidu.com/s/1cpMM0xWZ1Dxs8HhVAmeUkA 提取码: a36e