一、用线性回归找到最佳拟合直线
1.1 线性回归
回归的目的是预测数值型的目标值。最直接的方法就是找到回归方程Y=X.T*w。其中w称作回归系数,求这些回归系数的过程就是回归。一个常用的方法就是找出使误差最小的w。这里的误差是指预测y值和真实y值之间的平方差值。由于使用该误差的简单累加将使得正差值和负差值相互抵消,所以我们采用平方误差。
回归的一般方法:
- 收集数据:采用任意方法收集数据。
- 准备数据:回归需要数值型数据,标称型数据将被转成二值型数据。
- 分析数据:绘出数据的可视化二维图将有助于对数据做出理解和分析,在采用缩减法求得新回归系数之后, 可以将新拟合线绘在图上作为对比。
- 训练算法:找到回归系数。
- 测试算法:使用R^2或者预测值和数据的拟合度,来分析模型的效果。
- 使用算法:使用回归,可以在给定输入的时候预测出一个数值,这是对分类方法的提升,因为这样可以预测连续型数据而不仅仅是离散的类别标签。
1.2 代码实现
# -*- coding: utf-8 -*-
"""
Created on Fri May 4 15:35:23 2018
@author: lizihua
"""
from numpy import mat,linalg,corrcoef
import matplotlib.pyplot as plt
#加载数据
def loadDataSet(fileName):
numFeat = len(open(fileName).readline().split('\t'))-1
dataMat = [];labelMat = []
fr = open(fileName)
for line in fr.readlines():
lineArr = []
curLine = line.strip().split('\t')
for i in range(numFeat):
lineArr.append(float(curLine[i]))
dataMat.append(lineArr)
labelMat.append(float(curLine[-1]))
return dataMat, labelMat
#计算最佳拟合直线
#w的最优解的表达式:w=(X.T*X).I*(X.T*y)
def standRegres(xArr,yArr):
xMat = mat(xArr); yMat = mat(yArr).T
xTx = xMat.T*xMat
#若矩阵的行列式不为零,则该矩阵一定可逆
#Numpy中的linalg库中的det()方法可以计算矩阵的行列式
if linalg.det(xTx) == 0.0:
print("This matrix is singular, cannot do inverse")
return
#矩阵A.I代表求矩阵A的逆矩阵
ws = xTx.I *(xMat.T * yMat)
return ws
#绘制数据图形
def plot(xArr,yArr,ws):
xcord=[]
for i in range(len(xArr)):
xcord.append(xArr[i][1])
fig = plt.figure()
ax = fig.add_subplot(111)
ax.scatter(xcord,yArr, marker='o', s=50)
yHat = mat(xArr)*ws
ax.plot(xcord,yHat,'g')
plt.show()
return yHat
#测试
if __name__ == "__main__":
xArr,yArr = loadDataSet('ex0.txt')
print("x的前两条数据:\n",xArr[:2])
#result:x的前两条数据: [[1.0, 0.067732], [1.0, 0.42781]]
#注意:x数据中X0总是1
ws = standRegres(xArr,yArr)
print("ws:\n",ws)
yHat = plot(xArr,yArr,ws)
print("相关系数:\n",corrcoef(yHat.T,yArr))
1.3 结果显示
二、局部加权线性回归(Locally Weighted Linear Regression,LWLR)
局部加权线性回归算法就是我们给待预测点附件的每个点都赋予一定的权重;然后在这个带有权重的新数据集上基于最小均方误差来进行普通的回归。
2.1 基本思想
普通的线性回归:
使得均方误差最小,得: