机器学习 - 多项式回归

多项式回归,回归函数是回归多变量多项式的回归。多项式回归也是线性回归模型其中的一种。由于任一函数都可以用多项式进行拟合,因此多项式回归有着广泛的应用。

本文分为 理论介绍Python 示例代码 两部分

👉 点此直接跳转到示例代码

理论介绍

多项式回归

线性回归模型形式比较简单,且有很好的解释性,但是它只适用于 X 和 Y 之间存在线性关系的数据集。对于非线性关系的数据集,线性回归不能很好的工作。 本节将介绍线性回归模型的扩展–多项式回归,可以用用它拟合非线性关系的数据集。

多项式回归,回归函数是回归多变量多项式的回归。多项式回归也是线性回归模型其中的一种。由于任一函数都可以用多项式进行拟合,因此多项式回归有着广泛的应用。

研究一个因变量与一个或多个自变量之间的回归分析,成为多项式回归。 如果自变量只有一个,则称为一元多项式回归,如果自变量有多个时,则称为多元多项式回归。在一元回归分析中,如果因变量与自变量的关系是非线性的,可以采用一元多项式回归。

一元 n 次多项式回归方程为:

$$ \widehat y= \theta _ {0} + \theta _ {1} x+ \theta _ {0} x^ {2} + \cdots + \theta _ {n} x^ {7} $$

数据并不是线性关系的,这个时候我们可以使用一元多项式回归来拟合。

一元多项式回归函数:

$$ y(x, \theta )= \theta _ {0} + \theta _ {1} x+ \theta _ {2} x^ {2} + \cdots + \theta _ {n} x^ {n} = \sum _ {j=0} nw_ {j} x^ {j} $$

$n$ 表示多项式的阶数,$x^j$ 表示 $x$ 的 $j$ 次幂,$w$ 则代表该多项式的系数。

当使用多项式去拟合三点时,需要确定两个要素:

  1. 多项式系数 $\theta$
  2. 多项式阶数 $n$

利用 sklearn 中的 PolynomialFeatures 构造多项式

在 sklearn 中,可以通过 PolynomialFeatures() 类自动产生多项式特征矩阵。

1
sklearn.preprocessing.PolynomialFeatures(degree=2, interaction_only=False, include_bias=True)
  • degree: 多项式次数,默认为 2 次多项式。
  • interaction_only: 默认为 False,如果为 True 则产生相互影响的特征集。
  • include_bias: 默认为 True,包含多项式中的截距项。
1
2
3
4
5
sklearn.preprocessing import PolynomialFeatures  
# degree 代表多项式的的最高次  
transfer = PolynomialFeatures(degree=2, include_bias=False)  
# 将 x 训练成多项式形式的数据  
x = transfer.fit_transform(x)  

生成用于多项式回归的数据

1
2
3
4
5
def genY(x):  
    a0, a1, a2, a3, e = 0.01, -0.2, 0.3, -0.04, 0.05  
    yr = a0 + a1 * x + a2 * (x ** 2) + a3 * (x ** 3) + e  
    y = yr + 0.03 * np.random.rand(1)  
    return y

使用 numpy 生成线性数据:

1
x = np.linspace(-1, 1, 200)

利用公式计算出每个 x 对于的 y 值:

1
y = [genY(a) for a in x]

公式中生成一个一元三次的数据(这条语句在其中加入噪声点进行干扰。):

1
y = yr + 0.03 * np.random.rand(1)

最后将处理 x 和 y 的形状方便用于计算:

1
2
x = x.reshape(-1, 1)
y = np.array(y).reshape(-1, 1)

使用线性回归预测:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
# 导入线性回归类  
from sklearn.linear_model import LinearRegression  
# 实例化  
lr = LinearRegression()  
# 传入数据进行训练  
lr.fit(x, y)  
# 传入数据进行模型评估  
score = lr.score(x, y)
# 导入用于数据分割的函数  
from sklearn.model_selection import train_test_split  
# 将数据集分割成训练集和测试集  
# test_size=0.2 表示将 20 的数据用于测试  
x_train, x_test, y_train, y_test = train_test_split(x, y, test_size=0.2)  

Python 示例代码

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
import numpy as np
from sklearn.linear_model import LinearRegression
from sklearn.preprocessing import PolynomialFeatures
from sklearn.model_selection import train_test_split

np.random.seed(100)


def gen_y(x):
    a0, a1, a2, a3, e = 0.01, -0.2, 0.3, -0.04, 0.05
    yr = a0 + a1 * x + a2 * (x ** 2) + a3 * (x ** 3) + e
    y = yr + 0.03 * np.random.rand(1)
    return y


def model_train(x, y):
    # 利用 PolynomialFeatures 类构造多项式的数据,并设置最高次为 3
    poly_features = PolynomialFeatures(degree=3)
    x_poly = poly_features.fit_transform(x)

    # 将特征值拆分成训练集和测试集
    x_train, x_test, y_train, y_test = train_test_split(x_poly, y, test_size=0.2, random_state=42)

    # 实例化出一个线性回归分类器
    lin_reg = LinearRegression()

    # 传入训练数据训练模型
    lin_reg.fit(x_train, y_train)

    # 使用 score 函数对模型进行评估
    score = lin_reg.score(x_test, y_test)

    return score


if __name__ == '__main__':
    # 利用 np 中的 linspace 生成线性数据
    x = np.linspace(-1, 1, 200)
    # 用公式算出 y
    y = [gen_y(a) for a in x]
    x = x.reshape(-1, 1)
    y = np.array(y).reshape(-1, 1)
    print(model_train(x, y))

输出:0.9965995795138225