上一篇博客讲到了线性回归,这一篇我们来讲一讲多远线性回归。我个人看来这两者没有什么本质的区别,无非是特征的数量不同。线性回归只有一个特征,就是X是一维的,而多元线性回归特征是多维的。两者的计算公式也相同。
为了节省空间我们只讲精要,加载数据和标签的两个子函数请看我上一遍博客!这里不再粘贴出来。
首先,还是理论:
我们可以看到多元线性回归依然使用的是梯度下降法,和前面的线性回归一样。
只不过在学习率的选择上有些变化,在线性回归中,学习率是我们自己凭感觉选择的,这当然不能保证是最优的。其实这里也是人工选择的,具体做法是尝试多个学习率,绘制成图,选择最佳学习率。
下面贴出我的代码:
if __name__ == "__main__":
x = load_data('ex3x.dat')
y = load_label('ex3y.dat')
#print x,y
x = np.mat(x)
y = np.mat(y).transpose()
#print x,y
sigma = np.std(x,0)
mu = np.mean(x,0)
#print sigma,mu
#print sigma[:,1]
x[:,1] = (x[:,1] - mu[:,1])/sigma[:,1]
x[:,2] = (x[:,2] - mu[:,2])/sigma[:,2]
m,n = np.shape(x)
theat = np.mat(np.zeros(n))
lr = [1.0]
plt.figure(1)
ax1 = plt.subplot(111)
for l in lr:
J = []
for i in range(50):
j = []
h = np.dot(x,theat.transpose())
det_h = h - y
det_t = l*(1.0/m)*np.dot(det_h.transpose(),x)
theat = theat - det_t
J.append((1.0/2*m)*np.dot(det_h.transpose(),det_h))
#print theat
for i in range(50):
j.append(float(J[i][0]))
plt.figure(1)
plt.plot(range(50),j[:])
plt.sca(ax1)
plt.show()
写这段简单的代码,给我的打击不小呀,虽然最后完成了,但是发现自己的python水平还是不行,在此也提醒大家,编程这活,不等懈怠呀,要时时练习才行。废话不多说了,简单讲一下我遇到的问题和解决方法!
(1)数据的归一化
数据的归一化是机器学习,图像处理中经常要做的事情,但是在python下我还是首次
sigma = np.std(x,0)
mu = np.mean(x,0)
#print sigma,mu
#print sigma[:,1]
x[:,1] = (x[:,1] - mu[:,1])/sigma[:,1]
x[:,2] = (x[:,2] - mu[:,2])/sigma[:,2]
在此说明X的类型是矩阵,这里我又遇到两个问题,第一个是计算方差和均值是出错,第二个是取矩阵元素是出错。
第一个问题,我已开始写的代码是:
sigma = np.std(x)
mu = np.mean(x)
注意到没,我没有加上第二个参数,这就导致我计算出的方差和均值是所有元素的方差和均值,而我的最终目的是按列计算,
所以加上第二个参数0很重要!第二个参数为1 表示按行计算!
第二个问题,就是对于取矩阵元素。
取矩阵中的元素与取列表中的元素相同,我使用的切片的方法,如果你有好的方法,希望留言告知我,在此感谢!
(2)画图
本来想详细讲一下,不过发现内容太多了,我将会在Python模块学习系列中详细讲到
这里只解释:
for i in range(50):
j.append(float(J[i][0]))
这里的J是列表形式,每个元素又是矩阵(我都不知道我怎么生成了这么个变量),现在我想把J变成一个list形式,这样才能方便画图。
j.append(float(J[i][0]))
注意:float()函数是
把列表中的矩阵元素变换成了浮点型元素,这个很重要!