使用 scikit-learn 实现非线性回归树
介绍
回归是一种预测连续结果的监督机器学习技术。回归算法主要有两种类型 - 线性和非线性。虽然线性模型很有用,但它们依赖于独立变量和因变量之间存在线性关系的假设。在实际商业环境中,这一假设通常很难满足。这就是非线性回归算法发挥作用的地方,它能够捕捉数据中的非线性。
在本指南中,我们将重点介绍回归树和随机森林,它们是基于树的非线性算法。与往常一样,第一步是了解问题陈述。
问题陈述
在本指南中,我们将尝试构建回归算法来预测经济中的失业率。本项目使用的数据来自 [https://research.stlouisfed.org/fred2] 提供的美国经济时间序列数据。数据包含 574 行和 5 个变量,如下所述:
- psavert——个人储蓄率。
- pce——个人消费支出,以十亿美元计。
- uempmed - 失业平均持续时间,以周为单位。
- pop- 总人口数,以千为单位。
- 失业 – 失业人数(千人)(因变量)。
评估指标
我们将使用两个指标来评估模型的性能——R 平方值和均方根误差 (RMSE)。理想情况下,较低的 RMSE 和较高的 R 平方值表明模型良好。
步骤
在本指南中,我们将遵循以下步骤:
步骤 1——加载所需的库和模块。
第 2 步——加载数据并执行基本数据检查。
步骤 3-为特征和响应变量创建数组。
步骤4-创建训练和测试数据集。
步骤5-构建、预测和评估模型-决策树和随机森林。
以下部分将介绍这些步骤。
步骤 1 - 加载所需的库和模块
import pandas as pd
import numpy as np
from sklearn import model_selection
from sklearn.linear_model import LinearRegression
from sklearn.linear_model import Ridge
from sklearn.linear_model import Lasso
from sklearn.linear_model import ElasticNet
from sklearn.neighbors import KNeighborsRegressor
from sklearn.tree import DecisionTreeRegressor
from sklearn.svm import SVR
from sklearn.ensemble import RandomForestRegressor
from sklearn.metrics import r2_score
from sklearn.model_selection import train_test_split
from sklearn.metrics import mean_squared_error
from math import sqrt
import matplotlib.pyplot as plt
第 2 步 - 读取数据并执行基本数据检查
第一行代码将数据读入为 pandas 数据框,而第二行打印形状 - 5 个变量的 574 个观测值。第三行给出数值变量的汇总统计数据。
平均人口为 2.57 亿,而平均失业人数为 780 万。此外,没有缺失值,因为所有变量都有 574 个“计数”,等于数据中的记录数。另一个重要的观察结果是变量规模的差异。虽然人口范围在 1.98 亿到 3.21 亿之间;但个人储蓄率“psavert”的范围在 1.9% 到 17% 之间。这种规模差异需要标准化。
df = pd.read_csv('regressionexample.csv')
print(df.shape)
df.describe()
输出:
(574, 5)
| | pce | pop | psavert | uempmed | unemploy |
|-------|--------------|---------------|------------|------------|--------------|
| count | 574.000000 | 574.000000 | 574.000000 | 574.000000 | 574.000000 |
| mean | 4843.510453 | 257189.381533 | 7.936585 | 8.610105 | 7771.557491 |
| std | 3579.287206 | 36730.801593 | 3.124394 | 4.108112 | 2641.960571 |
| min | 507.400000 | 198712.000000 | 1.900000 | 4.000000 | 2685.000000 |
| 25% | 1582.225000 | 224896.000000 | 5.500000 | 6.000000 | 6284.000000 |
| 50% | 3953.550000 | 253060.000000 | 7.700000 | 7.500000 | 7494.000000 |
| 75% | 7667.325000 | 290290.750000 | 10.500000 | 9.100000 | 8691.000000 |
| max | 12161.500000 | 320887.000000 | 17.000000 | 25.200000 | 15352.000000 |
步骤 3 - 为特征和响应变量创建数组
第一行代码创建了一个名为“target_column”的目标变量对象。第二行给出了除目标变量“unemploy”之外的所有特征的列表。
上面我们已经看到,变量的单位有很大差异,可能会影响建模过程。为了防止这种情况,我们将通过将预测变量缩放到 0 到 1 之间来进行规范化。第三行执行此任务。
第四行显示标准化数据的摘要。我们可以看到,所有独立变量现在都已在 0 到 1 之间缩放。目标变量保持不变。
target_column = ['unemploy']
predictors = list(set(list(df.columns))-set(target_column))
df[predictors] = df[predictors]/df[predictors].max()
df.describe()
输出:
| | pce | pop | psavert | uempmed | unemploy |
|-------|------------|------------|------------|------------|--------------|
| count | 574.000000 | 574.000000 | 574.000000 | 574.000000 | 574.000000 |
| mean | 0.398266 | 0.801495 | 0.466858 | 0.341671 | 7771.557491 |
| std | 0.294313 | 0.114466 | 0.183788 | 0.163020 | 2641.960571 |
| min | 0.041722 | 0.619258 | 0.111765 | 0.158730 | 2685.000000 |
| 25% | 0.130101 | 0.700857 | 0.323529 | 0.238095 | 6284.000000 |
| 50% | 0.325087 | 0.788627 | 0.452941 | 0.297619 | 7494.000000 |
| 75% | 0.630459 | 0.904651 | 0.617647 | 0.361111 | 8691.000000 |
| max | 1.000000 | 1.000000 | 1.000000 | 1.000000 | 15352.000000 |
步骤 4 - 创建训练和测试数据集
我们将在训练集上构建模型,并评估其在测试集上的表现。下面的前几行代码分别创建独立变量 (X) 和因变量 (y) 的数组。第三行将数据分为训练数据集和测试数据集,其中“test_size”参数指定要保留在测试数据中的数据百分比。第四行打印训练集 (4 个变量的 401 个观测值) 和测试集 (4 个变量的 173 个观测值) 的形状。
X = df[predictors].values
y = df[target_column].values
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.30, random_state=40)
print(X_train.shape); print(X_test.shape)
输出:
(401, 4)
(173, 4)
第 5 步 - 构建、预测和评估模型 - 决策树和随机森林
在此步骤中,我们将使用 scikit-learn 库实现各种基于树的非线性回归模型。
决策树
决策树,也称为分类和回归树 (CART),适用于分类和连续输入和输出变量。它的工作原理是根据独立变量中最重要的分割器将数据分成两个或多个同质集。最好的区分器是最小化成本指标的那个。分类树的成本指标通常是熵或基尼指数,而对于回归树,默认指标是均方误差。
决策树的基本工作流程如下:
建模过程从根节点开始,根节点代表整个数据。它被分成两个或多个子节点,也称为分裂。分裂过程持续到满足分裂标准为止,分裂发生的子节点称为决策节点。一旦满足分裂标准,节点就不会进一步分裂;这样的节点称为叶节点或终端节点。我们还可以通过称为修剪的过程删除子节点。
现在,我们将使用 DecisionTreeRegressor 类创建一个 CART 回归模型。第一步是实例化下面第一行代码中完成的算法。第二行将模型拟合到训练集上。使用的参数是max_depth(表示树的最大深度)和min_samples_leaf(表示叶节点所需的最小样本数)。
dtree = DecisionTreeRegressor(max_depth=8, min_samples_leaf=0.13, random_state=3)
dtree.fit(X_train, y_train)
输出:
DecisionTreeRegressor(criterion='mse', max_depth=8, max_features=None,
max_leaf_nodes=None, min_impurity_decrease=0.0,
min_impurity_split=None, min_samples_leaf=0.13,
min_samples_split=2, min_weight_fraction_leaf=0.0,
presort=False, random_state=3, splitter='best')
一旦在训练集上建立了模型,我们就可以进行预测了。下面的第一行代码在训练集上进行预测。第二行和第三行代码在训练集上打印评估指标 - RMSE 和 R 平方。在第四行到第六行中,在测试数据集上重复相同的步骤。
# Code lines 1 to 3
pred_train_tree= dtree.predict(X_train)
print(np.sqrt(mean_squared_error(y_train,pred_train_tree)))
print(r2_score(y_train, pred_train_tree))
# Code lines 4 to 6
pred_test_tree= dtree.predict(X_test)
print(np.sqrt(mean_squared_error(y_test,pred_test_tree)))
print(r2_score(y_test, pred_test_tree))
输出:
1176.4038283170603
0.807082155638476
1180.376221946623
0.7849943413269588
上面的输出显示,训练数据的 RMSE 为 1,176,404,测试数据的 RMSE 为 1,180,376。另一方面,训练数据的 R 平方值为 80.7%,测试数据的 R 平方值为 78.5%。这些数字还不错,但可以通过参数调整实现更多改进。我们将更改参数“max_depth”的值,以查看它如何影响模型性能。
下面的前四行代码分别实例化并拟合“max_depth”参数为 2 和 5 的回归树。第五行和第六行代码对训练数据生成预测,而第七行和第八行代码对测试数据进行预测。
# Code Lines 1 to 4: Fit the regression tree 'dtree1' and 'dtree2'
dtree1 = DecisionTreeRegressor(max_depth=2)
dtree2 = DecisionTreeRegressor(max_depth=5)
dtree1.fit(X_train, y_train)
dtree2.fit(X_train, y_train)
# Code Lines 5 to 6: Predict on training data
tr1 = dtree1.predict(X_train)
tr2 = dtree2.predict(X_train)
#Code Lines 7 to 8: Predict on testing data
y1 = dtree1.predict(X_test)
y2 = dtree2.predict(X_test)
下面的代码为第一个回归树“dtree1”生成评估指标 - RMSE 和 R 平方。
# Print RMSE and R-squared value for regression tree 'dtree1' on training data
print(np.sqrt(mean_squared_error(y_train,tr1)))
print(r2_score(y_train, tr1))
# Print RMSE and R-squared value for regression tree 'dtree1' on testing data
print(np.sqrt(mean_squared_error(y_test,y1)))
print(r2_score(y_test, y1))
输出:
1184.4861869175104
0.8044222060059463
1339.4870036355467
0.7231235652677634
上述“dtree1”模型的输出显示,训练数据的 RMSE 为 1,184,486,测试数据的 RMSE 为 1,339,487。训练数据的 R 平方值为 80.4%,测试数据的 R 平方值为 72.3%。该模型在两个评估指标中的表现均低于之前的模型。
我们现在将通过运行以下代码行来检查决策树模型“dtree2”的性能。
# Print RMSE and R-squared value for regression tree 'dtree2' on training data
print(np.sqrt(mean_squared_error(y_train,tr2)))
print(r2_score(y_train, tr2))
# Print RMSE and R-squared value for regression tree 'dtree2' on testing data
print(np.sqrt(mean_squared_error(y_test,y2)))
print(r2_score(y_test, y2))
输出:
562.5285929502469
0.9558888127723508
686.4818444997242
0.9272777851696767
上面的输出显示了与早期模型相比的显著改进。训练集和测试集的 RMSE 分别降至 562,529 和 686,482。另一方面,训练集和测试集的 R 平方值分别增加到 95.6% 和 92.7%。这表明“max_depth”参数为 5 的回归树模型表现更好,展示了参数调整如何提高模型性能。
随机森林(或引导聚合)
免责声明:本内容来源于第三方作者授权、网友推荐或互联网整理,旨在为广大用户提供学习与参考之用。所有文本和图片版权归原创网站或作者本人所有,其观点并不代表本站立场。如有任何版权侵犯或转载不当之情况,请与我们取得联系,我们将尽快进行相关处理与修改。感谢您的理解与支持!
请先 登录后发表评论 ~