Scikit Learn 随机梯度下降


在这里,我们将了解 Sklearn 中的一种优化算法,称为随机梯度下降 (SGD)。

随机梯度下降 (SGD) 是一种简单而有效的优化算法,用于找到最小化成本函数的函数参数/系数的值。换句话说,它用于在 SVM 和 Logistic 回归等凸损失函数下对线性分类器进行判别学习。它已成功应用于大规模数据集,因为系数更新是针对每个训练实例执行的,而不是在实例结束时执行。

SGD 分类器


随机梯度下降 (SGD) 分类器基本上实现了一个简单的 SGD 学习例程,支持各种损失函数和分类惩罚。 

Scikit-learn 提供SGDClassifier模块来实现 SGD 分类。

参数

下表是 SGDClassifier 模块使用的参数:

序号参数及说明
1

loss: str,默认 = ‘hinge’

它表示实现时要使用的损失函数。默认值是“hinge”,它会给我们一个线性 SVM。其他可以使用的选项是:

  • log:这个损失会给我们逻辑回归,即一个概率分类器。

  • modified_huber:平滑损失,带来对异常值的容忍度以及概率估计。

  • squared_hinge: 类似于'hinge' loss,但它是二次惩罚的。

  • perceptron:它是感知器算法使用的线性损失。

2

penalty: str, ‘none’, ‘l2’, ‘l1’, ‘elasticnet’

它是模型中使用的正则化项。默认为 L2。我们可以使用 L1 或“elasticnet”;同样,但两者都可能给模型带来稀疏性,因此 L2 无法实现。

3

alpha: float,默认 = 0.0001

Alpha 是与正则化项相乘的常数,是决定我们想要惩罚模型的程度的调整参数。默认值为 0.0001。

4

l1_ratio: float,默认 = 0.15

这称为 ElasticNet 混合参数。它的范围是 0 < = l1_ratio < = 1。如果 l1_ratio = 1,惩罚将是 L1 惩罚。如果 l1_ratio = 0,惩罚将是 L2 惩罚。

5

fit_intercept: bool, 默认=True

此参数指定应将常数(偏差或截距)添加到决策函数中。在计算中将不使用截距,如果设置为 false,则假定数据已经居中。

6

tol: float 或 none,optional,默认 = 1.e-3

此参数表示迭代的停止标准。它的默认值是 False 但如果设置为 None,迭代将在 ?loss>best_loss - n_iter_no_change 的 tol连续的时代。

7

shuffle: bool,optional,默认 = True

这个参数代表我们是否希望我们的训练数据在每个 epoch 之后被打乱。

8

verbose:int,默认=0

它代表详细程度。其默认值为 0。

9

epsilon:float,默认= 0.1

此参数指定不敏感区域的宽度。如果 loss = ‘epsilon-insensitive’,则当前预测与正确标签之间小于阈值的任何差异都将被忽略。

10

max_iter: int, optional, 默认 = 1000

顾名思义,它代表了历元上的最大传递次数,即训练数据。

11

warm_start : bool,optional,默认= false

将此参数设置为 True,我们可以重用之前调用 fit 作为初始化的解决方案。如果我们选择默认值,即 false,它将删除之前的解决方案。

12

random_state: int, RandomState 实例或None,optional,默认= none

此参数表示在混洗数据时使用的生成的伪随机数的种子。以下是选项。

  • int: 在这种情况下,随机状态(random_state)是随机数生成器使用的种子。

  • 随机状态实例(RandomState instance): 在这种情况下,随机状态(random_state)是随机数生成器。

  • None: 在这种情况下,随机数生成器是 np.random 使用的 RandonState 实例。

13

n_jobs: int 或 none,optional,默认 = None

它表示用于 OVA(一个对所有)计算的 CPU 数量,用于多类问题。默认值为 none,表示 1。

14

learning_rate: 字符串,optional,默认 = ‘最优’

  • 如果学习率是‘constant’,eta = eta0;

  • 如果学习率是‘optimal’,eta = 1.0/(alpha*(t+t0)),其中 t0 由 Leon Bottou 选择;

  • 如果学习率 = ‘invscalling’,eta = eta0/pow(t, power_t)。

  • 如果学习率 = ‘adaptive’,eta = eta0。

15

eta0: double, 默认= 0.0

它代表上述学习率选项的初始学习率,即“constant”、“invscalling”或“adaptive”。

16

power_t: idouble,默认=0.5

它是“incscalling”学习率的指数。

17

early_stopping: bool,默认= False

此参数表示在验证分数没有提高时使用提前停止来终止训练。它的默认值是 false 但当设置为 true 时,它会自动留出一部分训练数据作为验证,并在验证分数没有提高时停止训练。

18

validation_fraction:float,默认= 0.1

它仅在 early_stopping 为真时使用。它表示为提前终止训练数据而留出作为验证集的训练数据的比例。

19

n_iter_no_change: int, 默认=5

它表示算法在提前停止之前运行时没有改进的迭代次数。

20

classs_weight: dict, {class_label: weight} or “balanced”, or None, optional

此参数表示与类关联的权重。如果未提供,则类的权重应该为 1。

21average: iBoolean 或 int,optional,默认 = false

它表示用于 OVA(一个对所有)计算的 CPU 数量,用于多类问题。默认值为 none,表示 1。

属性

下表是 SGDClassifier 模块使用的属性:

序号属性和描述
1

coef_: array, shape (1, n_features) if n_classes==2, else (n_classes, n_features)

此属性提供分配给要素的权重。

2

intercept_: array, shape (1,) if n_classes==2, else (n_classes,)

它代表决策函数中的独立项。

3

n_iter_: int

它给出了达到停止标准的迭代次数。

示例

与其他分类器一样,随机梯度下降 (SGD) 必须拟合以下两个数组:

  • 保存训练样本的数组 X,它的大小为 [n_samples, n_features]。

  • 保存目标值的数组 Y,即训练样本的类标签。它的大小为 [n_samples]。

以下 Python 脚本使用 SGDClassifier 线性模型:

import numpy as np
from sklearn import linear_model
X = np.array([[-1, -1], [-2, -1], [1, 1], [2, 1]])
Y = np.array([1, 1, 2, 2])
SGDClf = linear_model.SGDClassifier(max_iter = 1000, tol=1e-3,penalty = "elasticnet")
SGDClf.fit(X, Y)
SGDClassifier(
    alpha = 0.0001, average = False, class_weight = None,
    early_stopping = False, epsilon = 0.1, eta0 = 0.0, fit_intercept = True,
    l1_ratio = 0.15, learning_rate = 'optimal', loss = 'hinge', max_iter = 1000,
    n_iter = None, n_iter_no_change = 5, n_jobs = None, penalty = 'elasticnet',
    power_t = 0.5, random_state = None, shuffle = True, tol = 0.001,
    validation_fraction = 0.1, verbose = 0, warm_start = False
)

现在,一旦拟合,模型可以预测新值如下:

SGDClf.predict([[2.,2.]])
array([2])

对于上面的例子,我们可以借助以下python脚本来获取权重向量:

SGDClf.coef_
array([[19.54811198, 9.77200712]])

同样,我们可以借助以下python脚本来获取intercept的值:

SGDClf.intercept_
array([10.])

我们可以通过使用 SGDClassifier.decision_function 来获得与超平面的有符号距离,如下面的python脚本中使用的那样:

SGDClf.decision_function([[2., 2.]])
array([68.6402382])

SGD 回归器


随机梯度下降 (SGD) 回归器基本上实现了一个简单的 SGD 学习例程,支持各种损失函数和惩罚来拟合线性回归模型。

Scikit-learn提供 SGDRegressor 模块来实现SGD回归。

参数

SGDRegressor使用的参数与SGDClassifier模块中使用的参数几乎相同,区别在于 "loss"参数。对于SGDRegressor模块的loss参数,其正值如下:

  • squared_loss: 指的是普通最小二乘拟合。

  • huber:SGDRegressor: 通过从平方损失转换为线性损失超过 epsilon 的距离来校正异常值。 “huber”的工作是修改“squared_loss”,使算法不再关注纠正异常值。

  • epsilon_insensitive: 实际上,它忽略了小于 epsilon 的错误。

  • squared_epsilon_insensitive: 与 epsilon_insensitive 相同。唯一的区别是它变成了超过 epsilon 容差的平方损失。

另一个区别是名为'power_t'的参数的默认值是0.25,而不是SGDClassifier中的0.5,此外,它没有'class_weight'和'n_jobs'参数。

属性

SGDRegressor 的属性也与 SGDClassifier 模块的属性相同。但是,它具有三个额外的属性,如下所示:

  • average_coef_:array,形状(n_features,)

顾名思义,它提供分配给特征的平均权重。

  • average_intercept_: array,形状(1,)

顾名思义,它提供了平均截距项。

  • t_: int

它提供了在训练阶段执行的权重更新次数。

注意: 属性average_coef_ 和average_intercept_ 将在启用参数“average”为True 后起作用。

示例

以下Python脚本使用 SGDRegressor 线性模型:

import numpy as np
from sklearn import linear_model
n_samples, n_features = 10, 5
rng = np.random.RandomState(0)
y = rng.randn(n_samples)
X = rng.randn(n_samples, n_features)
SGDReg =linear_model.SGDRegressor(
    max_iter = 1000,penalty = "elasticnet",loss = 'huber',tol = 1e-3, average = True
)
SGDReg.fit(X, y)
SGDRegressor(
    alpha = 0.0001, average = True, early_stopping = False, epsilon = 0.1,
    eta0 = 0.01, fit_intercept = True, l1_ratio = 0.15,
    learning_rate = 'invscaling', loss = 'huber', max_iter = 1000,
    n_iter = None, n_iter_no_change = 5, penalty = 'elasticnet', power_t = 0.25,
    random_state = None, shuffle = True, tol = 0.001, validation_fraction = 0.1,
    verbose = 0, warm_start = False
)

现在,我们可以借助以下python脚本获得权重向量:

SGDReg.coef_
array([-0.00423314, 0.00362922, -0.00380136, 0.00585455, 0.00396787])

同样,我们可以借助以下python脚本来获取intercept的值:

SGReg.intercept_
SGReg.intercept_

我们可以借助以下python脚本获取训练阶段权重更新的次数:

SGDReg.t_
61.0

SGD 的利弊


遵循SGD的优点:

  • 随机梯度下降 (SGD) 非常有效。

  • 它很容易实现,因为有很多代码调整的机会。

遵循SGD的缺点:

  • 随机梯度下降 (SGD) 需要几个超参数,如正则化参数。

  • 它对特征缩放很敏感。