线性回归基础知识_20201208

一,什么是线性回归(Linear Regression)

1.1 线性回归的概念

线性:两个变量之间的关系是一次函数关系的——图象是直线,叫做线性。
非线性:两个变量之间的关系不是一次函数关系的——图象不是直线,叫做非线性。
回归:人们在测量事物的时候因为客观条件所限,求得的都是测量值,而不是事物真实的值,为了能够得到真实值,无限次的进行测量,最后通过这些测量数据计算回归到真实值,这就是回归的由来。

1.2线性回归解决的问题

解决的就是通过已知的数据得到未知的结果。例如:对房价的预测、判断信用评价、电影票房预估等,只能做回归问题。
模型选择:
在觉得特征和标签之间有线性关系时选择,实际工作中如果无法确定是否有线性相关关系,可以通过试来看

二,线性回归的决策函数和损失函数

2.1决策函数

h(x):预测值
sata:每个特征的权重
x:已知的
公式如下:
在这里插入图片描述
也可以写成如下格式:
在这里插入图片描述
公式中x是我们已知的,为了得到预测值h(x),我们还需要知道sata的值,sata的求解就引出了损失函数和优化方法,也可以说,sata的求解就是损失函数优化的过程,求得一个最优的sata,使得h(x)最接近真实值。

2.2 损失函数(Loss Function–mse)

损失函数指的是预测值与真实值之间的差异,线性回归这里用的是欧式距离表示损失函数,公式如下:
在这里插入图片描述
这个公式就是著名的最小二乘损失,

补充知识
最小二乘法(又称最小平方法)是一种数学优化技术。它通过最小化误差的平方和寻找数据的最佳函数匹配。

MSE:mean-square error,均方误差,是损失函数的一种。
最小二乘法在公式上是和MSE一样的,但是他另外一个概念是可以直接求解。

三,线性回归优化方法

优化过程就是使损失函数最小时,sata的值,有两种方法进行求解,一种是最小二乘法(直接对参数求导),一种是梯度下降法。

3.1 最小二乘法(最小均方差)(了解)

求解过程如下:
1.损失函数如下:
在这里插入图片描述
2.对损失函数求导
在这里插入图片描述
3.为了使损失函数最小,就令其倒数为0,解得sata值如下:
在这里插入图片描述

最小二乘法需要计算(XTX)−1逆矩阵,有可能逆矩阵不存在,这样就没有办法直接用最小二乘法,所以就引出了梯度下降法
补充知识
常见函数求导公式如下:
在这里插入图片描述
符合函数求导方法
链式法则

3.2 梯度下降法(非常重要)

目标:寻找某个凸函数的最小值。
凸函数: 某段区间只有一个低谷的函数

含义:朝着导数变小的方向逐步更新参数
梯度:导数的方向
分类:梯度下降分为批量梯度下降和随机梯度下降

3.2.1最小均方算法(LMS)

我们首先随便给θ一个初始化的值,然后改变θ值让J(θ)的取值变小,不断重复改变θ使J(θ)变小的过程直至J(θ)约等于最小值.
首先我们给θ一个初试值,然后向着让J(θ)变化最大的方向更新θ的取值,如此迭代。公式如下:
在这里插入图片描述
公式中α称为步长(learning rate),它控制θ每次向J(θ)变小的方向迭代时的变化幅度。J(θ)对θ的偏导表示J(θ)变化最大的方向。由于求的是极小值,因此梯度方向是偏导数的反方向。求解一下这个偏导,过程如下:
在这里插入图片描述
那么θ的迭代公式就变为:
在这里插入图片描述
这是当训练集只有一个样本时的数学表达。我们又两种方式将只有一个样本的数学表达转化为样本为多个的情况:梯度下降(gradient descent)和正则方程(The normal equations)。这里我们重点讲梯度下降。

3.2.2 梯度下降

梯度下降的步骤
init(w):一般为均值为0,方差为1的分布的随机值,比如0.2,如果是别的值,比如100,更新次数会比较大.init(b)也是一样的方法
随机取一个值 x0;
算出对应的 f(x0);
计算 f(x0)处损失函数 f(x)的导数;
从 f(x0)开始,沿着该处导数的方向增加 αα ,取值为x1,也就是说:|x0-x1|/ αα 的值为f(x) 在f(x0)的斜率;
重复循环2-4步,直到达到退出条件(比如设定循环N次后停止)
在这里插入图片描述
上式可以理解为w = w+dota(w)
alaph是学习率
一般合适的步幅是0.01,代表更新的步幅,如果设置的比较小,更新的次数就会比较多,更新的比较慢,这个值究竟怎么设置呢?一般设置为0.05,0.1这样比较大的步幅,检代码运行的是不是有问题,在一个看其他参数调的是否已经合适了,

3.2.2.1 批梯度下降

批梯度下降(batch gradient descent)

如下公式是处理一个样本的表达式:

在这里插入图片描述

转化为处理多个样本就是如下表达:

在这里插入图片描述

这种新的表达式每一步都是计算的全部训练集的数据,所以称之为批梯度下降(batch gradient descent)。

注意,梯度下降可能得到局部最优,但在优化问题里我们已经证明线性回归只有一个最优点,因为损失函数J(θ)是一个二次的凸函数,不会产生局部最优的情况。(假设学习步长α不是特别大)

批梯度下降的算法执行过程如下图:
在这里插入图片描述

大家仔细看批梯度下降的数学表达式,每次迭代的时候都要对所有数据集样本计算求和,计算量就会很大,尤其是训练数据集特别大的情况。那有没有计算量较小,而且效果也不错的方法呢?有!这就是:随机梯度下降(Stochastic Gradient Descent, SGD)

3.2.2.2 随机梯度下降

随机梯度下降在计算下降最快的方向时时随机选一个数据进行计算,而不是扫描全部训练数据集,这样就加快了迭代速度。随机梯度下降并不是沿着J(θ)下降最快的方向收敛,而是震荡的方式趋向极小点。余凯教授在龙星计划课程中用“曲线救国”来比喻随机梯度下降。
随机梯度下降表达式如下:
在这里插入图片描述
执行过程如下图:
在这里插入图片描述
批梯度下降和随机梯度下降在三维图上对比如下:
在这里插入图片描述

3.2.3 梯度下降总结

线性回归是回归问题中的一种,线性回归假设目标值与特征之间线性相关,即满足一个多元一次方程。使用最小二乘法构建损失函数,用梯度下降来求解损失函数最小时的θ值。

挑战与问题:局部极小值
解决:优化方法合集详细讲解

四,线性回归过拟合/欠拟合解决方案

多项式回归:
含有X的高次项,对于模型的拟合能力更强,损失函数更小。
在这里插入图片描述

4.1 什么是过拟合/欠拟合

在这里插入图片描述
欠拟合:在训练集上拟合程度不高。
过拟合:在训练集上拟合程度很高,在测试集上拟合程度很低
解决过拟合的方式有很多种(early stopping、数据集扩增(Data augmentation)、正则化(Regularization)包括L1、L2(L2 regularization也叫weight decay),dropout),其中一种就是改变损失函数,加入正则化项。
使用正则化项,也就是给loss function加上一个参数项,正则化项有L1正则化、L2正则化。加入这个正则化项好处:

  • 控制参数幅度,不让模型“无法无天”。

  • 限制参数搜索空间

  • 解决欠拟合与过拟合的问题。

4.2 L1正则化(lasso回归)

在损失函数后面加上正则化项形成新的损失函数,
在这里插入图片描述
lamda是我们手动指定的,一般是很小的,并且是需要我们调节的一个参数
在这里插入图片描述
比原始的更新规则多出了η * λ * sgn(w)/n这一项。当w为正时,更新后的w变小。当w为负时,更新后的w变大——因此它的效果就是让w往0靠,使网络中的权重尽可能为0,也就相当于减小了网络复杂度,防止过拟合。

另外,上面没有提到一个问题,当w为0时怎么办?当w等于0时,|W|是不可导的,所以我们只能按照原始的未经正则化的方法去更新w,这就相当于去掉ηλsgn(w)/n这一项,所以我们可以规定sgn(0)=0,这样就把w=0的情况也统一进来了。(在编程的时候,令sgn(0)=0,sgn(w>0)=1,sgn(w<0)=-1)
L1正则化使用的场景

L1正则化(Lasso回归)可以使得一些特征的系数变小,甚至还使一些绝对值较小的系数直接变为0,从而增强模型的泛化能力 。对于高的特征数据,尤其是线性关系是稀疏的,就采用L1正则化(Lasso回归),或者是要在一堆特征里面找出主要的特征,那么L1正则化(Lasso回归)更是首选了。**总结一句话就是觉得特征太多的话,使用L1正则化就比较好。**没有需要特征筛选的场景就不要使用L1正则化,尤其是我们后面讲到的深度神经网络。

4.3 L2 正则化(岭回归_权重衰减)

4.3.1 以梯度下降解释正则化过程

在损失函数后面加上正则化项形成新的损失函数,
在这里插入图片描述
然后求导:
在这里插入图片描述
对于h(x)=wx+b的决策函数,正则化之后对b是没有影响的,只是影响了w的权重,让w的权重变小了,如下:
在这里插入图片描述
每一次迭代,θ j 都要先乘以一个小于1的因子(即( 1 − α λ m ),从而使得θ j 不断减小,因此总的来看,θ是不断减小的。
以上的目的使w的权重变小了,为什么w的权重变小能够预防过拟合呢?理由如下:
过拟合的时候,拟合函数的系数往往非常大,为什么?如下图所示,过拟合,就是拟合函数需要顾忌每一个点,最终形成的拟合函数波动很大。在某些很小的区间里,函数值的变化很剧烈。这就意味着函数在某些小区间里的导数值(绝对值)非常大,由于自变量值可大可小,所以只有系数足够大,才能保证导数值很大。
而正则化是通过约束参数的范数使其不要太大,所以可以在一定程度上减少过拟合情况。

在这里插入图片描述

4.3.2 为什么L2权重衰减就能防止过拟合?

如果参数过大,数据偏移一点点,就对结果有很大影响,如果参数很小,即使数据有较大偏移,对结果也不会有很大的影响,这就意味着小参数能适应不同的数据集,也在一定程度上避免了过拟合。4.3.1中就以梯度下降为例解释了正则化怎么讲参数变小。

4.4 L1正则化和L2正则化的对比(重点)

  • L2正则化只能解决矩阵不可逆的问题,L1正则化可以还可以解决多重共线性问题。
  • L1正则化可以产生稀疏权值矩阵,即产生一个稀疏模型,可以用于特征选择
  • L2正则化可以防止模型过拟合(overfitting);一定程度上,L1也可以防止过拟合
  • 适用场景的不同
    只要数据线性相关,用LinearRegression拟合的不是很好,需要正则化,可以考虑使用岭回归(L2), 如何输入特征的维度很高,而且是稀疏线性关系的话, 岭回归就不太合适,考虑使用Lasso回归。
    L1正则化(Lasso回归)可以使得一些特征的系数变小,甚至还使一些绝对值较小的系数直接变为0,从而增强模型的泛化能力 。对于维度高的特征数据,尤其是线性关系是稀疏的,就采用L1正则化(Lasso回归),或者是要在一堆特征里面找出主要的特征,那么L1正则化(Lasso回归)更是首选了。

L1和L2为了使w1.w2这个参数更小,为什么一个更小的参数使有必要加上来呢?
因为当参数值很大的时候,会造成过拟合现象,就是说参数值w占的比重太大了,造成输入很大的X和很小的X,结果输出都差不多。就不满足了真实的分布,所以要将参数值变小。

4.5 正则化对梯度下降的影响

为什么需要对数值型特征做归一化呢?我们不妨借助随机梯度下降的实例来 说明归一化的重要性。假设有两种数值型特征,x1的取值范围为 [0, 10],x2的取值 范围为[0, 3],于是可以构造一个目标函数符合图1.1(a)中的等值图。 在学习速率相同的情况下,x1的更新速度会大于x2,需要较多的迭代才能找到 最优解。如果将x1和x2归一化到相同的数值区间后,优化目标的等值图会变成图 1.1(b)中的圆形,x1和x2的更新速度变得更为一致,容易更快地通过梯度下降找 到最优解。
在这里插入图片描述
可以看出归一化对梯度下降的影响是很大的,所以在实际应用中通过梯度下降求解的算法通常都是需要进行归一化的,常见的有线性回归、逻辑回归、支持向量机、神经网络等模型。
但对于决策树模型则并不适用,以C4.5为例,决策树在进行节点分裂时主要 依据数据集D关于特征x的信息增益比,而信息增益比跟特征 是否经过归一化是无关的,因为归一化并不会改变样本在特征x上的信息增益。

4.6 Python中的L1和L2的直观理解(重点)

这部分内容将解释为什么L1正则化可以产生稀疏模型(L1是怎么让系数等于零的),以及为什么L2正则化可以防止过拟合
L1正则化公式:
在这里插入图片描述
令后面我们加上的惩罚项(正则化项)等于L,alafa是正则化系数,现在我们的问题就变成了在L约束下求J0的最下值。
J0叫做损失函数,也可以叫做梯度下降函数
以二维系数为例,画出J0和L的图像:
在这里插入图片描述
性质: 1.面积表征正则项函数的值的大小
2.对于损失函数的等值线,随机取w1,w2的组合采样情况,可以发现,只有取切点部分能保证整体最小 、
alafa越小,左下角的矩形越大,J0与L的第一个交点就是最优解,这个交点很容易在坐标轴上,造成系数wi为零,形成稀疏矩阵,说明L1正则化很容易得到稀疏解(解向量中0较多)

稀疏矩阵是有利于特征选择的,稀疏矩阵说明只有少数特征对这个模型有影响,我们只用关注这些系数非0的特征,比如垃圾邮件分类中,以词做为特征向量,就可以帮助我们筛选掉一些不重要的特征。
如果是用在不需要特征筛选的场景L1就是不好的,

同样可以画出他们在二维平面上的图形,如下:
在这里插入图片描述
L表示为图中的黑色圆形,随着梯度下降法的不断逼近,与圆第一次产生交点,而这个交点很难出现在坐标轴上。这就说明了L2正则化不容易得到稀疏矩阵,同时为了求出损失函数的最小值,使得w1和w2无限接近于0(laimuta要足够大),达到防止过拟合的问题。L2范数能让解比较小(靠近0),但是比较平滑(不等于0)。

因为不会产生稀疏矩阵,L2正则化更加常用,我们一般说的正则化也是指L2正则化。

4.7 解决过拟合的补充资料

解决过拟合的方法一是特征选择,而是正则化,下面进行详细阐述。同样给出五个点,有两种模型进行拟合,如下图,很明显右图是有过拟合嫌疑的
在这里插入图片描述
怎样解决过拟合呢?一种方法是进行特征选择,将无用的特征变量x3,x4去掉(可以手动去掉,也可以使用算法去掉),但是有时候我们不希望直接去掉变量的值,一是因为特征选择的不确定性,二是因为这个过程复杂,所以我们一般是选择第二种方式解决过拟合的问题,正则化,正则化的本质就是减少参数(sata3,sata4)的值,但是保留变量。
要减少sata3,sata4的值,就可以在损失函数后面加上如下图蓝色字体,这样在最小化目标函数时,因为 前面加了很大的参数,sata3,sata4就会很小,达到目标,但是实际使用中我们我们很南确定对哪些参数进行正则化,所以都是对所有参数进行正则化的。
在这里插入图片描述
对所有特征进行正则化:
在这里插入图片描述

在这里插入图片描述
是正则项,这里是没有包括sta0的,所以lambda不能太大,否则造成除了lambda以外的参数都比较小,目标值十分接近常数值,造成欠拟合。

4.8弹性网络回归(ElasticNet回归)

损失函数(目标函数)的公式如下:
在这里插入图片描述
使用场景
ElasticNet在我们发现用Lasso回归太过(太多特征被稀疏为0),而岭回归也正则化的不够(回归系数衰减太慢)的时候,可以考虑使用ElasticNet回归来综合,得到比较好的结果。

一般也不常用,当需要做特征筛选的时候就用L1 ,不需要特征筛选的话就用L2.

五,6. 线性回归要求因变量服从正态分布?

我们假设线性回归的噪声服从均值为0的正态分布。 当噪声符合正态分布N(0,delta2)时,因变量则符合正态分布N(ax(i)+b,delta2),其中预测函数y=ax(i)+b。这个结论可以由正态分布的概率密度函数得到。也就是说当噪声符合正态分布时,其因变量必然也符合正态分布。

在用线性回归模型拟合数据之前,首先要求数据应符合或近似符合正态分布,否则得到的拟合函数不正确,比如房价就是满足正态分布的,对于不满足正态分布的需要做一些处理,对特征也是要求满足正态分布的,但是互联网上是有大量不满足正态分布的数据。

【重要】对于不满足正态分布的数据怎么用? 加Log进行特征的预处理,将特征拉到一个正态分布。

六.深刻理解为何正则能解决过拟合问题

[有兴趣可以自查]加2范数正则等价于加了高斯分布的先验,加1范数正则相当于加拉普拉斯分布先验。

七,应用中的注意事项

1.特征标量需要进行缩放(数值型特特征一定要进行缩放)
也就是进行标准化,有广义的标准化和狭义的标准化,狭义的标注啊是指Z-score标准化(数据均值为0,方差为1的分布),广义的标准化是我们可以做最大最小标准化。

梯度下降更快更好地优化(等值线法向量朝向圆心)

2.学习率的选择
以适中的学习率进行其他超参数的调试,最终训练时减小学习率

3.lasso和ridge的选择/L1&L2正则化的选择
当特征是机器抽取,且维度很高,需要进行特征选择的时候选L1正则化;其他时候选L2

为什么L1正则不常用:L1正则化并不是处处连续的,所以优化的时候会有一定难度,且优化速度慢

正则化重点汇总
1.L1,L2正则化的公式
2.L1,L2正则化使用的场景
3.L1产生稀疏解的解释(画图解释)

为什么要进行正则化?(数值型特征进行缩放)
1.精度问题,计算机系统里对一个数据数值的定义是有边界的,如果这个数值过大,就会限制模型的发挥。
比如现在x1分布在【0-1】,x2分布在【0-1000】,y分布在【0-1】,这个时候w2就要很小很小,比如是0.0001.

在这里插入图片描述

2.梯度下降的时候,梯度下降的方向是按照切线的垂直方向前进的,圆是直接朝着圆心最小处下降的,椭圆的话不是朝着圆心,造成迂回成本较高。
在这里插入图片描述
所以总结下:只要使用到梯度下降的地方就要进行特征的缩放,否则很影响学习。

线性回归最小案例:

%matplotlib inline
import matplotlib.pyplot as plt
def runplt():
    plt.figure()
    plt.title(u'diameter-cost curver')
    plt.xlabel(u'diameter')
    plt.ylabel(u'cost')
    plt.axis([0, 25, 0, 25])
    plt.grid(True)
    return plt

plt = runplt()
X = [[6], [8], [10], [14], [18]]
y = [[7], [9], [13], [17.5], [18]]
plt.plot(X, y, 'k.')
plt.show()

在这里插入图片描述

from sklearn.linear_model import LinearRegression
import numpy as np
# 创建并拟合模型
model = LinearRegression()
model.fit(X, y)
print('预测:$%.2f' % model.predict(np.array([12]).reshape(-1, 1))[0])

在这里插入图片描述

plt = runplt()
plt.plot(X, y, 'k.')
X2 = [[0], [10], [14], [25]]
model = LinearRegression()
model.fit(X, y)
y2 = model.predict(X2)
plt.plot(X, y, 'k.')
plt.plot(X2, y2, 'g-') # 颜色 and 线形

# 残差预测值
yr = model.predict(X)
for idx, x in enumerate(X):
    plt.plot([x, x], [y[idx], yr[idx]], 'r-')

plt.show()

在这里插入图片描述

import numpy as np
from sklearn.linear_model import LinearRegression
from sklearn.preprocessing import PolynomialFeatures
X_train = [[6], [8], [10], [14], [18]]
y_train = [[7], [9], [13], [17.5], [18]]
X_test = [[6], [8], [11], [16]]
y_test = [[8], [12], [15], [18]]
regressor = LinearRegression()
regressor.fit(X_train, y_train)
xx = np.linspace(0, 26, 100)
yy = regressor.predict(xx.reshape(xx.shape[0], 1))
plt = runplt()
plt.plot(X_train, y_train, 'k.')
plt.plot(xx, yy)

quadratic_featurizer = PolynomialFeatures(degree=2)
X_train_quadratic = quadratic_featurizer.fit_transform(X_train)
X_test_quadratic = quadratic_featurizer.transform(X_test)
regressor_quadratic = LinearRegression()
regressor_quadratic.fit(X_train_quadratic, y_train)
xx_quadratic = quadratic_featurizer.transform(xx.reshape(xx.shape[0], 1))
plt.plot(xx, regressor_quadratic.predict(xx_quadratic), 'r-')
plt.show()
print(X_train)
print(X_train_quadratic)
print(X_test)
print(X_test_quadratic)
print('1 r-squared', regressor.score(X_test, y_test))
print('2 r-squared', regressor_quadratic.score(X_test_quadratic, y_test))
?PolynomialFeatures

在这里插入图片描述
在这里插入图片描述

plt = runplt()
plt.plot(X_train, y_train, 'k.')

quadratic_featurizer = PolynomialFeatures(degree=2)
X_train_quadratic = quadratic_featurizer.fit_transform(X_train)
X_test_quadratic = quadratic_featurizer.transform(X_test)
regressor_quadratic = LinearRegression()
regressor_quadratic.fit(X_train_quadratic, y_train)
xx_quadratic = quadratic_featurizer.transform(xx.reshape(xx.shape[0], 1))
plt.plot(xx, regressor_quadratic.predict(xx_quadratic), 'r-')

cubic_featurizer = PolynomialFeatures(degree=3)
X_train_cubic = cubic_featurizer.fit_transform(X_train)
X_test_cubic = cubic_featurizer.transform(X_test)
regressor_cubic = LinearRegression()
regressor_cubic.fit(X_train_cubic, y_train)
xx_cubic = cubic_featurizer.transform(xx.reshape(xx.shape[0], 1))
plt.plot(xx, regressor_cubic.predict(xx_cubic))
plt.show()
print(X_train_cubic)
print(X_test_cubic)
print('2 r-squared', regressor_quadratic.score(X_test_quadratic, y_test))
print('3 r-squared', regressor_cubic.score(X_test_cubic, y_test))

在这里插入图片描述
在这里插入图片描述

plt = runplt()
plt.plot(X_train, y_train, 'k.')

quadratic_featurizer = PolynomialFeatures(degree=2)
X_train_quadratic = quadratic_featurizer.fit_transform(X_train)
X_test_quadratic = quadratic_featurizer.transform(X_test)
regressor_quadratic = LinearRegression()
regressor_quadratic.fit(X_train_quadratic, y_train)
xx_quadratic = quadratic_featurizer.transform(xx.reshape(xx.shape[0], 1))
plt.plot(xx, regressor_quadratic.predict(xx_quadratic), 'r-')

seventh_featurizer = PolynomialFeatures(degree=7)
X_train_seventh = seventh_featurizer.fit_transform(X_train)
X_test_seventh = seventh_featurizer.transform(X_test)
regressor_seventh = LinearRegression()
regressor_seventh.fit(X_train_seventh, y_train)
xx_seventh = seventh_featurizer.transform(xx.reshape(xx.shape[0], 1))
plt.plot(xx, regressor_seventh.predict(xx_seventh))
plt.show()
print('2 r-squared', regressor_quadratic.score(X_test_quadratic, y_test))
print('7 r-squared', regressor_seventh.score(X_test_seventh, y_test))

在这里插入图片描述

猜你喜欢

转载自blog.csdn.net/a18829292719/article/details/109449617