多项式回归:线性回归的扩展
多项式回归:线性回归的扩展
多项式回归是线性回归的扩展,它通过加入输入数据的高次项和交叉项,帮助我们更好地捕捉那些非线性关系。简单来说,它让我们用线性回归的方式去处理更复杂的数据模式。本文通过实例展示了多项式回归与线性回归的对比,讲解了如何选择合适的多项式阶数,以及这些选择如何影响模型的拟合效果。最后,还介绍了它的优缺点以及常见的应用场景,帮助大家在实际问题中做出更明智的选择。
1. 算法简介
在经典的线性回归中,我们假设输入变量与输出变量之间存在线性关系:
y=β0+β1x+ϵ
y = \beta_0 + \beta_1 x + \epsilon
y=β0+β1x+ϵ
然而,在许多实际问题中,这种线性关系往往过于简单。例如,物体下落的位移随时间是二次关系,经济学中的收益随投入可能呈现非线性增长。此时,单纯的线性回归无法捕捉这种非线性模式。
多项式回归(Polynomial Regression) 正是为了解决这一问题而提出的。
它的核心思想是:通过扩展特征(即把输入变量的高次项作为新的特征),将非线性问题转化为线性回归来求解。
因此,多项式回归并不是一个全新的回归算法,而是线性回归的扩展。
例如:
- 二次回归(Quadratic Regression) 就是多项式回归在阶数 d=2d=2 的特例。
- 更高阶的回归(如三次、四次)也是同理。
2. 数学模型
2.1 一维情况
对于一维输入 xxx,阶数为 ddd 的多项式回归模型为:
y=β0+β1x+β2x2+⋯+βdxd+ϵ
y = \beta_0 + \beta_1 x + \beta_2 x^2 + \dots + \beta_d x^d + \epsilon
y=β0+β1x+β2x2+⋯+βdxd+ϵ
这里,模型对参数 β\betaβ 仍然是线性的,只是增加了新的特征 x2,x3,…,xdx^2, x^3, \dots, x^dx2,x3,…,xd。
2.2 多维情况
如果输入是 X=(x1,x2,…,xp)X = (x_1, x_2, \dots, x_p)X=(x1,x2,…,xp),则不仅包括每个特征的高次项,还包括交叉项。例如在二次回归中:
y=β0+∑i=1pβixi+∑i=1pβiixi2+∑i=1p∑j=i+1pβijxixj+ϵ
y = \beta_0 + \sum_{i=1}^p \beta_i x_i + \sum_{i=1}^p \beta_{ii} x_i^2 + \sum_{i=1}^p \sum_{j=i+1}^p \beta_{ij} x_i x_j + \epsilon
y=β0+i=1∑pβixi+i=1∑pβiixi2+i=1∑pj=i+1∑pβijxixj+ϵ
这种特征扩展由 scikit-learn 的 PolynomialFeatures
自动完成。
3. 参数说明
from sklearn.linear_model import LinearRegression
from sklearn.preprocessing import PolynomialFeatures
from sklearn.pipeline import Pipeline# 线性回归模型
linear = LinearRegression(*,fit_intercept=True, # 是否计算截距项。True 表示模型会计算截距项 β_0,False 表示不计算(即截距为0)。copy_X=True, # 是否复制输入数据。True 表示会创建输入数据的副本,False 表示会直接修改原数据。n_jobs=None, # 并行计算的工作线程数。None 表示使用单线程,如果是整数,则表示使用该数量的 CPU 核心。positive=False, # 是否约束模型的回归系数为正数。True 会强制系数非负,默认 False。
)# 多项式特征生成器
poly = PolynomialFeatures(degree=2, # 多项式的阶数。degree=2 表示进行二次回归,即使用 x, x^2 作为特征。*,interaction_only=False, # 是否只生成交互项,而不包括特征的高次项。如果为 True,只会生成 x_i * x_j 的交叉项,不包括 x_i^2 这种单独的高次项。include_bias=True, # 是否在特征中包含常数项(x^0 = 1)。True 表示包括常数项,默认为 True。order='C', # 特征生成的顺序。'C' 表示按列优先顺序排列,'F' 则表示按行优先顺序排列。这通常影响计算效率,但不改变最终结果。
)# 管道(Pipeline)将多步骤操作链接在一起
Pipeline(steps, *,transform_input=None, # 数据预处理时的输入格式。如果需要进行复杂的输入处理,可以定义该参数。memory=None, # 如果为 True,会缓存步骤中的中间结果以加快计算速度。如果为 None,则不使用缓存。verbose=False # 是否显示中间计算过程的详细信息。True 会打印出每一步的计算细节,默认为 False。
)# 以下是如何通过管道(Pipeline)结合多项式回归与线性回归模型
poly_reg = Pipeline([("poly", PolynomialFeatures(degree=4, include_bias=False)), # 第一步:多项式特征生成,degree=4 表示使用四次方特征,include_bias=False 表示不加常数项。("linear", LinearRegression()) # 第二步:使用线性回归模型来拟合扩展后的多项式特征。
]).fit(X, y) # 训练模型
在 scikit-learn 中,多项式回归通常用 PolynomialFeatures
+ LinearRegression
或者 Pipeline
来实现。
- PolynomialFeatures
degree
:多项式的阶数(如degree=2
表示二次回归)。interaction_only
:是否只考虑交叉项而不包含平方项等。include_bias
:是否添加常数列(默认为True
)。
- LinearRegression
fit_intercept
:是否拟合截距项。positive
:是否约束模型的回归系数为正数(默认为False
)。
通过组合这两个模块,可以方便地构建多项式回归模型。
4. 实例:多项式回归 vs 线性回归
下面的例子展示了多项式回归和线性回归在同一数据上的效果对比:
import numpy as np
import matplotlib.pyplot as plt
import seaborn as sns
from sklearn.linear_model import LinearRegression
from sklearn.preprocessing import PolynomialFeatures
from sklearn.pipeline import Pipelinesns.set_theme(style="whitegrid", font="SimHei", rc={"axes.unicode_minus": False})# 固定随机种子
np.random.seed(42)# 1. 构造数据:来自 4 次多项式 + 噪声
X = np.linspace(-3, 3, 120).reshape(-1, 1)
x = X.flatten()
y = (0.02 * x**4 - 0.1 * x**3 + 0.3 * x**2 - 0.8 * x + 2).reshape(-1, 1)
y = y + np.random.randn(len(X), 1) * 0.5 # 加噪声# 2. 普通线性回归
lin_reg = LinearRegression().fit(X, y)# 3. 多项式回归
poly_reg = Pipeline([("poly", PolynomialFeatures(degree=4, include_bias=False)),("linear", LinearRegression())
]).fit(X, y)# 4. 可视化
X_plot = np.linspace(-3, 3, 300).reshape(-1, 1)plt.figure(figsize=(8, 6))
plt.scatter(X, y, color="blue", s=25, label="数据点")plt.plot(X_plot, lin_reg.predict(X_plot), "g-", lw=2, label="线性回归")
plt.plot(X_plot, poly_reg.predict(X_plot), "r-", lw=2, label="多项式回归")plt.title("线性回归 vs 多项式回归", fontsize=14)
plt.xlabel("X", fontsize=12)
plt.ylabel("y", fontsize=12)
plt.legend()
plt.grid(alpha=0.3)
plt.show()
5. 多项式阶数的影响
多项式的阶数直接决定了模型的拟合能力与灵活性。
- 阶数过低:模型太简单,容易发生欠拟合,无法有效捕捉数据的真实模式;
- 阶数适中:模型能够较好地拟合数据,捕捉到数据的主要趋势;
- 阶数过高:模型过于复杂,容易发生过拟合,甚至对数据中的噪声敏感。
通过对正弦函数的拟合实验(分别使用 degree=1, 3, 5, 10),可以直观观察到阶数变化对拟合效果的显著影响。
import numpy as np
import matplotlib.pyplot as plt
import seaborn as sns
from sklearn.linear_model import LinearRegression
from sklearn.preprocessing import PolynomialFeatures
from sklearn.pipeline import Pipelinesns.set_theme(style="whitegrid", font="SimHei", rc={"axes.unicode_minus": False})# 数据:正弦函数
X = np.linspace(0, 2*np.pi, 100).reshape(-1, 1)
y = np.sin(X) + 0.1*np.random.randn(100, 1)degrees = [1, 3, 5, 10]
plt.figure(figsize=(12, 8))for i, d in enumerate(degrees, 1):model = Pipeline([("poly", PolynomialFeatures(degree=d)),("linear", LinearRegression())]).fit(X, y)plt.subplot(2, 2, i)plt.scatter(X, y, s=15, c="blue", label="数据点")plt.plot(X, model.predict(X), c="red", label=f"degree={d}")plt.title(f"多项式回归 (degree={d})")plt.legend()plt.grid(alpha=0.3)plt.suptitle("多项式回归参数对拟合效果的影响", fontsize=16)
plt.tight_layout()
plt.show()
结果分析:
- degree=1:模型为直线,明显欠拟合,未能很好地捕捉正弦波的波动。
- degree=3:模型开始跟随部分正弦波,但仍有偏差,尚未完全拟合。
- degree=5:模型能够较好地拟合正弦波,效果较好。
- degree=10:模型出现过度弯曲,产生振荡现象,明显过拟合,过度捕捉了数据中的噪声。
6. 应用示例
- 物理学:自由落体运动的位移–时间关系、电路中的非线性响应。
- 经济学:投入–产出关系、边际效应建模。
- 工程学:传感器曲线拟合、设备能耗与时间关系建模。
- 医学:药物剂量与疗效曲线。
7. 算法总结
- 本质:多项式回归是线性回归的扩展,通过特征映射提升拟合非线性关系的能力。
- 特例:二次回归是其特殊情况。
- 优点:实现简单,可解释性强,能够处理一定程度的非线性。
- 缺点:高阶时易过拟合,特征数迅速膨胀,计算复杂度增加。
- 实践建议:
- 先从低阶模型开始,逐步提升阶数;
- 使用交叉验证选择合适的阶数;
- 对复杂非线性问题,可以考虑核方法或神经网络等更强大的模型。