Python数据科学:正则化方法

大数据 数据可视化
本文主要介绍,Python数据科学:正则化方法。正则化方法的出现,通过收缩方法(正则化方法)进行回归。正则化方法主要包括岭回归与LASSO回归。

本文主要介绍,Python数据科学:正则化方法。正则化方法的出现,通过收缩方法(正则化方法)进行回归。

正则化方法主要包括岭回归与LASSO回归。

一、岭回归

岭回归通过人为加入的惩罚项(约束项),对回归系数进行估计,为有偏估计。

有偏估计,允许估计有不大的偏度,以换取估计的误差显著减小,并在其残差平方和为最小的原则下估计回归系数。

通常岭回归方程中的R²会稍低于线性回归分析,但回归系数的显著性往往明显高于普通线性回归。

这里不对相应的理论知识进行细说,说实话小F也是晕乎乎...

所以选择先调包,看看效果是啥样的。

使用机器学习框架scikit-learn进行岭回归参数的选择(正则化系数)。

数据是书中的数据,已上传网盘,公众号回复「正则化」,即可获取。

scikit-learn当中的模型不会默认对数据标准化,必须手动执行。

标准化后的数据可以消除量纲,让每个变量的系数在一定意义下进行直接比较。

  1. import numpy as np 
  2. import pandas as pd 
  3. import matplotlib.pyplot as plt 
  4. from sklearn.linear_model import Ridge 
  5. from sklearn.linear_model import RidgeCV 
  6. from sklearn.preprocessing import StandardScaler 
  7.  
  8. # 消除pandas输出省略号情况及换行情况 
  9. pd.set_option('display.max_columns', 500) 
  10. pd.set_option('display.width', 1000) 
  11. # 读取数据,skipinitialspace:忽略分隔符后的空白 
  12. df = pd.read_csv('creditcard_exp.csv', skipinitialspace=True
  13. # 获取信用卡有支出的行数据 
  14. exp = df[df['avg_exp'].notnull()].copy().iloc[:, 2:].drop('age2', axis=1) 
  15. # 获取信用卡无支出的行数据,NaN 
  16. exp_new = df[df['avg_exp'].isnull()].copy().iloc[:, 2:].drop('age2', axis=1) 
  17.  
  18. # 选择4个连续变量,分别是年龄 收入 当地小区价格 当地人均收入 
  19. continuous_xcols = ['Age''Income''dist_home_val''dist_avg_income'
  20. # 标准化 
  21. scaler = StandardScaler() 
  22. # 解释变量,二维数组 
  23. X = scaler.fit_transform(exp[continuous_xcols]) 
  24. # 被解释变量,一维数组 
  25. y = exp['avg_exp_ln'
  26.  
  27. # 生成正则化系数 
  28. alphas = np.logspace(-2, 3, 100, base=10) 
  29. # 使用不同的正则化系数对模型进行交叉验证 
  30. rcv = RidgeCV(alphas=alphas, store_cv_values=True
  31. # 使用数据集训练(fit) 
  32. rcv.fit(X, y) 
  33. # 输出最优参数,正则化系数及相应模型R² 
  34. print('The best alpha is {}'.format(rcv.alpha_)) 
  35. print('The r-square is {}'.format(rcv.score(X, y))) 
  36.  
  37. # 训练好后使用transform进行数据转换 
  38. X_new = scaler.transform(exp_new[continuous_xcols]) 
  39. # 使用模型对数据做预测 
  40. print(np.exp(rcv.predict(X_new)[:5])) 

输出结果如下。

Python数据科学:正则化方法

最优正则化系数为0.29,模型R²为0.475。

并使用最优正则化系数下的岭回归模型预测数据。

对不同正则化系数下模型的均方误差进行可视化。

  1. # 正则化系数搜索空间当中每轮交叉验证的结果,模型的均方误差 
  2. cv_values = rcv.cv_values_ 
  3. n_fold, n_alphas = cv_values.shape 
  4. # 模型均方误差上下波动值 
  5. cv_mean = cv_values.mean(axis=0) 
  6. cv_std = cv_values.std(axis=0) 
  7. ub = cv_mean + cv_std / np.sqrt(n_fold) 
  8. lb = cv_mean - cv_std / np.sqrt(n_fold) 
  9. # 绘制折线图,x轴是指数型形式 
  10. plt.semilogx(alphas, cv_mean, label='mean_score'
  11. # y1(lb)和y2(ub)之间进行填充 
  12. plt.fill_between(alphas, lb, ub, alpha=0.2) 
  13. plt.xlabel('$\\alpha$'
  14. plt.ylabel('mean squared errors'
  15. plt.legend(loc='best'
  16. plt.show() 

输出结果如下。

Python数据科学:正则化方法

发现正则化系数在40或50以下时,模型的均方误差相差不大。

当系数超过该阈值时,均方误差则快速上升。

所以正则化系数只要小于40或50,模型的拟合效果应该都不错。

  • 正则化系数越小则模型拟合越好,但过拟合情况也越容易发生。
  • 正则化系数越大,则越不容易过拟合,但模型的偏差越大。

RidgeCV通过交叉验证,可以快速返回“最优”的正则化系数。

当这只是基于数值计算的,可能最终结果并不符合业务逻辑。

比如本次模型的变量系数。

  1. # 输出模型的变量系数 
  2. print(rcv.coef_) 
  3. # 输出结果 
  4. [ 0.03321449 -0.30956185  0.05551208  0.59067449] 

发现收入的系数为负值,这肯定是不合理的。

下面通过岭迹图进行进一步分析。

岭迹图是在不同正则化系数下变量系数的轨迹。

  1. ridge = Ridge() 
  2. coefs = [] 
  3. # 不同正则化系数下的变量系数 
  4. for alpha in alphas: 
  5.     ridge.set_params(alpha=alpha) 
  6.     ridge.fit(X, y) 
  7.     coefs.append(ridge.coef_) 
  8.  
  9. # 绘制变量系数随正则化系数变化的轨迹 
  10. ax = plt.gca() 
  11. ax.plot(alphas, coefs) 
  12. ax.set_xscale('log'
  13. plt.xlabel('alpha'
  14. plt.ylabel('weights'
  15. plt.title('Ridge coefficients as a function of the regularization'
  16. plt.axis('tight'
  17. plt.show() 

输出结果。

Python数据科学:正则化方法

  • ①有两个变量的系数在不同的正则化系数下都很接近于0,那么可以选择删除。
  • ②正则化系数越大,对变量系数的惩罚越大,所有变量的系数都趋近于0。
  • ③有一个变量的系数变化非常大(有正有负),说明该系数的方差大,存在共线性的情况。

综合模型均方误差和岭迹图的情况,选取正则化系数为40。

  • 如果大于40,则模型均方误差增大,模型拟合效果变差。
  • 如果小于40,则变量系数不稳定,共线性没有得到抑制。

那么就来看看,当正则化系数为40时,模型变量系数的情况。

  1. ridge.set_params(alpha=40) 
  2. ridge.fit(X, y) 
  3. # 输出变量系数 
  4. print(ridge.coef_) 
  5. # 输出模型R² 
  6. print(ridge.score(X, y)) 
  7. # 预测数据 
  8. print(np.exp(ridge.predict(X_new)[:5])) 
  9. # 输出结果 
  10. [0.03293109 0.09907747 0.04976305 0.12101456] 
  11. 0.4255673043353688 
  12. [934.79025945 727.11042209 703.88143602 759.04342764 709.54172995] 

发现变量系数都为正值,符合业务直觉。

收入和当地人均收入这两个变量可以保留,另外两个删除。

二、LASSO回归

LASSO回归,在令回归系数的绝对值之和小于一个常数的约束条件下,使残差平方和最小化。

从而能够产生某些严格等于0的回归系数,得到解释力较强的模型。

相比岭回归,LASSO回归还可以进行变量筛选。

使用LassoCV交叉验证确定最优的正则化系数。

  1. # 生成正则化系数 
  2. lasso_alphas = np.logspace(-3, 0, 100, base=10) 
  3. # 使用不同的正则化系数对模型进行交叉验证 
  4. lcv = LassoCV(alphas=lasso_alphas, cv=10) 
  5. # 使用数据集训练(fit) 
  6. lcv.fit(X, y) 
  7. # 输出最优参数,正则化系数及相应模型R² 
  8. print('The best alpha is {}'.format(lcv.alpha_)) 
  9. print('The r-square is {}'.format(lcv.score(X, y))) 
  10.  
  11. # 输出结果 
  12. The best alpha is 0.04037017258596556 
  13. The r-square is 0.4426451069862233 

发现最优的正则化系数为0.04,模型R²为0.443。

接下来获取不同正则化系数下的变量系数轨迹。

  1. lasso = Lasso() 
  2. lasso_coefs = [] 
  3. # 不同正则化系数下的变量系数 
  4. for alpha in lasso_alphas: 
  5.     lasso.set_params(alpha=alpha) 
  6.     lasso.fit(X, y) 
  7.     lasso_coefs.append(lasso.coef_) 
  8.  
  9. # 绘制变量系数随正则化系数变化的轨迹 
  10. ax = plt.gca() 
  11. ax.plot(lasso_alphas, lasso_coefs) 
  12. ax.set_xscale('log'
  13. plt.xlabel('alpha'
  14. plt.ylabel('weights'
  15. plt.title('Lasso coefficients as a function of the regularization'
  16. plt.axis('tight'
  17. plt.show() 

输出结果。

Python数据科学:正则化方法

发现随着正则化系数的增大,所有变量的系数会在某一阈值突降为0。

其中缘由与LASSO回归方程有关,不细说。

输出LASSO回归的变量系数。

  1. print(lcv.coef_) 
  2. # 输出结果 
  3. [0.         0.         0.02789489 0.26549855] 

发现前两个变量被筛选掉了,即年龄和收入。

为啥和岭回归的结果不一样呢???

三、总结

坑留的有点多,待小F慢慢填...

责任编辑:未丽燕 来源: 法纳斯特
相关推荐

2021-08-30 11:40:06

PythonSeaborn可视化

2019-09-30 09:10:11

Python编程语言数据科学

2018-04-21 07:11:53

正则表达式Python函数

2018-11-06 20:30:23

Python开源工具机器学习

2018-12-18 13:32:37

方差分析数据分析教育

2019-05-07 19:12:28

机器学习神经网络Python

2021-10-08 13:45:23

大数据数据科学家货币

2020-11-18 14:40:46

数据科学自动化Uber

2023-09-22 11:32:31

数字化转型数字经济

2022-11-02 14:45:24

Python数据分析工具

2017-07-12 16:07:49

大数据数据可视化

2019-10-23 19:33:24

数据科学保护数据匿名化

2015-01-06 12:21:34

阿里云

2022-09-08 14:52:29

图数据库Neo4j

2018-06-27 10:45:12

数据Python程序

2019-03-20 14:17:21

数据科学PythonSQL

2019-03-19 09:00:14

Python 开发编程语言

2021-01-13 15:13:07

Python开发 工具

2018-04-16 11:11:56

2012-04-10 15:31:06

HTML 5
点赞
收藏

51CTO技术栈公众号