线性回归的原理
对于线性回归,其数据集是{(x1,y1),(x2,y2),,,,(xn,yn)},其中,xi=(xi1,,,,xid), d表示的是数据的维度,n表示样本数。对于线性回归的一般形式为:
对于θ的确定,使得f(x)无限接近y。我们采用均方误差的方式进行衡量f(x)和y的近似程度。即:
我们的目的就是学习θ,使得上面的损失最小。
那为什么用均方误差进行衡量呢?
极大似然估计(概率角度的诠释)
下面用极大似然估计,来解释为什么要用均方误差作为性能度量。
先讲一下什么是极大似然估计
极大似然估计,通俗理解来说,利用已知的样本结果信息,反过来猜测最有可能(最大概率)导致样本出现该结果的模型参数值。
也就是说在提供了一种给定观察数据来评估模型参数的方法。已知模型,确定参数。
我们把目标值和变量写成如下等式:
表示预测值和真实值之间的差距,我们假设是独立同分布,服从高斯分布。(根据中心极限定理)
所以带入上面的公式
因此对于所有样本,我们为了使得概率p最大化,因此有了如下:
我们为了让这个p达到最大,也就是L(θ)最大。这就是上面说的极大似然估计。为了方便计算,我们计算时通常对对数似然函数求最大值,所以会采用取对数的方式,将累乘转化成累加:
可以看出最大化l(θ)其实就是最小化
因此用均方误差来优化模型参数是很合理的。
线性回归损失函数、代价函数】目标函数
- 损失函数(Loss Function):
损失函数度量的是样本预测错误的程度(对于单个样本)。损失函数越小,拟合的程度越好,模型也就越好。
常用损失函数
-
0-1损失函数、
0-1 loss 是最原始的loss,它是一种较为简单的损失函数,如果预测值与目标值不相等,那么为1,否则为0,即:
0-1损失可用于分类问题,但是由于该函数是非凸的,在最优化过程中求解不方便,有阶跃,不连续。0-1 loss无法对x进行求导,在依赖于反向传播的深度学习任务中,无法被使用,所以使用不多。
2.平方损失函数、
平方损失函数标准形式如下:
特点:
(1)经常应用与回归问题
3.绝对损失函数、
绝对值损失函数是计算预测值与目标值的差的绝对值:
4.对数损失函数等
log对数损失函数的标准形式如下:
逻辑回归的损失函数就是log对数损失函数。
-
指数损失函数(exponential loss)
特点:
(1)对离群点、噪声非常敏感。经常用在AdaBoost算法中。
-
-
Hinge 损失函数
Hinge损失函数标准形式如下:
特点:
(1)hinge损失函数表示如果被分类正确,损失为0,否则损失就为1-yf(x)
SVM就是使用这个损失函数。
7.交叉熵损失函数 (Cross-entropy loss function)
交叉熵损失函数的标准形式如下:
本质上也是一种对数似然函数,可用于二分类和多分类任务中。
二分类问题中的loss函数(输入数据是softmax或者sigmoid函数的输出):
- 代价函数(cost Function):
代价函数是度量全部样本的平均误差。
多分类问题中的loss函数(输入数据是softmax或者sigmoid函数的输出):
当使用sigmoid作为激活函数的时候,常用交叉熵损失函数而不用均方误差损失函数,因为它可以完美解决平方损失函数权重更新过慢的问题,具有“误差大的时候,权重更新快;误差小的时候,权重更新慢”的良好性质.
常用的代价函数
- 均方误差、
2.均方根误差、
3.平均绝对误差
- 目标函数(Object Function):代价函数和正则化函数,最终要优化的函数。
线性回归的优化方法
-
梯度下降:
初始化参数θ 迭代使得J(θ)最小化:
即:
注:下标j表示第j个参数,上标i表示第i个数据点。
将所有的参数以向量形式表示,可得:
由于这个方法中,参数在每个数据点负梯度方面进行了移动,因此称为批梯度下降法对应的,我们可以每一次让参数只针对一个数据点进行移动,即:
每次只用一个样本的梯度进行更新,不是用所有样本的梯度进行更新,因此也叫随即梯度下降法。
随机梯度下降法的好处是,当数据点很多时,运行效率更高;
缺点是,因为每次只针对一个样本更新参数,未必找到最快路径达到最优值,甚至有时候会出现参数在最小值附近徘徊而不是立即收敛。但当数据量很大的时候,随机梯度下降法经常优于批梯度下降法。
当J为凸函数时,梯度下降法相当于让参数θ不断向J的最小值位置移动
梯度下降法的缺陷:如果函数为非凸函数,有可能找到的并非全局最优值,而是局部最优值。
-
最小二乘法矩阵求解:
令
对于x(i)
hθ(x)可以得到:
为最小化J(θ) ,对θ求导可得:
中间两项互为转置,由于求得的值是个标量,矩阵与转置相同,因此可以写成
令偏导数等于零,由于最后一项和θ无关,偏导数为0。
利用矩阵求导性质,
令导数等于零,
3、牛顿法
重复迭代,可以让逼近取到 𝑓(𝜃) 的最小值
当我们对损失函数 𝑙(𝜃) 进行优化的时候,实际上是想要取到 𝑙′(𝜃) 的最小值,因此迭代公式为:
𝜃:=𝜃−𝑙′(𝜃)𝑙″(𝜃)
其中,是对的偏导数,是的海森矩阵,
4、拟牛顿法
拟牛顿法的思路是用一个矩阵替代计算复杂的海森矩阵H,因此要找到符合H性质的矩阵。
要求得海森矩阵符合的条件,同样对泰勒公式求导
令 𝑥=𝑥1 ,即迭代后的值,代入可得:
更一般的,
𝑥𝑘 为第k个迭代值
即找到矩阵G,使得它符合上式。 常用的拟牛顿法的算法包括DFP,BFGS等,作为选学内容,有兴趣者可自行查询材料学习。
线性回归的评价指标
均方误差(MSE):平均绝对误差(MAE):
但以上评价指标都无法消除量纲不一致而导致的误差值差别大的问题,最常用的指标是R2,可以避免量纲不一致问题
R2也叫拟合优度,越接近1,表示可解释力度越大,模型拟合的效果越好。
R2_score = 1,样本中预测值和真实值完全相等,没有任何误差,表示回归分析中自变量对因变量的解释越好。
R2_score = 0。此时分子等于分母,样本的每项预测值都等于均值。
代码展示
生成数据:
#生成数据
import numpy as np
#生成随机数
np.random.seed(1234)
x = np.random.rand(500,3)
#构建映射关系,模拟真实的数据待预测值,映射关系为y = 4.2 + 5.7*x1 + 10.8*x2,可自行设置值进行尝试
y = x.dot(np.array([4.2,5.7,10.8]))
先尝试调用sklearn的线性回归模型训练数据:
import numpy as np
from sklearn.linear_model import LinearRegression
import matplotlib.pyplot as plt
%matplotlib inline
lr = LinearRegression(fit_intercept=True)
lr.fit(x,y)
print("估计的参数值为:%s" %(lr.coef_))
print('R2:%s' %(lr.score(x,y)))
x_test = np.array([2,4,5]).reshape(1,-1)
y_hat = lr.predict(x_test)
print("预测值为: %s" %(y_hat))
估计的参数值为:[ 4.2 5.7 10.8]
R2:1.0
预测值为: [85.2]
最小二乘法的矩阵求解
class LR_LS():
def __init__(self):
self.w = None
def fit(self, X, y):
# 最小二乘法矩阵求解
self.w = np.linalg.inv(X.T.dot(X)).dot(X.T).dot(y)
def predict(self, X):
y_pred = X.dot(self.w)
return y_pred
if __name__ == "__main__":
lr_ls = LR_LS()
lr_ls.fit(x,y)
print("估计的参数值:%s" %(lr_ls.w))
x_test = np.array([2,4,5]).reshape(1,-1)
print("预测值为: %s" %(lr_ls.predict(x_test)))
梯度下降法:
class LR_GD():
def __init__(self):
self.w = None
def fit(self,X,y,alpha=0.02,loss = 1e-10): # 设定步长为0.002,判断是否收敛的条件为1e-10
y = y.reshape(-1,1) #重塑y值的维度以便矩阵运算
[m,d] = np.shape(X) #自变量的维度
self.w = np.zeros((d)) #将参数的初始值定为0
tol = 1e5
#============================= show me your code =======================
while tol > loss:
h_f = X.dot(self.w).reshape(-1,1)
theta = self.w + alpha*np.mean(X*(y - h_f),axis=0) #计算迭代的参数值
tol = np.sum(np.abs(theta - self.w))
self.w = theta
#============================= show me your code =======================
def predict(self, X):
# 用已经拟合的参数值预测新自变量
y_pred = X.dot(self.w)
return y_pred
if __name__ == "__main__":
lr_gd = LR_GD()
lr_gd.fit(x,y)
print("估计的参数值为:%s" %(lr_gd.w))
x_test = np.array([2,4,5]).reshape(1,-1)
print("预测值为:%s" %(lr_gd.predict(x_test)))
思考
- 思考题:既然代价函数已经可以度量样本集的平均误差,为什么还要设定目标函数?
当模型复杂度增加时,有可能对训练集可以模拟的很好,但是预测测试集的效果不好,出现过拟合现象,这就出现了所谓的“结构化风险”。结构风险最小化即为了防止过拟合而提出来的策略
- 问题:请用泰勒展开法推导牛顿法公式
将 𝑓(𝑥) 用泰勒公式展开到第二阶,
对上式求导,并令导数等于0,求得x值
可以求得,
牛顿法的收敛速度非常快,但海森矩阵的计算较为复杂,尤其当参数的维度很多时,会耗费大量计算成本。我们可以用其他矩阵替代海森矩阵,用拟牛顿法进行估计,