什么是激活函数?
神经元节点中的函数f把输入信号的总和转化输出信号,这种函数一样平常称作激活函数。
激活函数的输出一样平常位于一个范围内(通常为 0 到 1 或 -1 到 1),详细取决于函数。因此,激活函数将节神经元节点输出归一化到设定的范围内。
选择何种激活函数将影响神经网络模型的结果和准确性。神经网络中的激活函数都是非线性函数,因为使用线性函数,神经网络中的层数就没有意义了。对于线性函数,不管如何加深层数,总是存在与之等效的无隐藏层神经网络。
神经网络中常用的激活函数
Sigmoid 函数
\(\Large \sigma(x) = \frac{1}{1+e^{-x}}\)
Sigmoid 函数具有以下优点:
- 梯度是连续光滑的
- 输出值在 0 到 1 之间,方便观察模型的输出是否符合预期。
- Sigmoid 函数的导数在 0 到 0.25 之间,可以控制反向传播过程中权值的更新幅度。
- Sigmoid 函数的输出接近 0 或 1 时,输出的导数接近 0,可以避免梯度消失的题目。
Sigmoid 也有一些缺点:
- Sigmoid 函数的输出在 0 到 1 之间,可能会导致梯度消失的题目,使得反向传播过程中权值的更新幅度变小。
- Sigmoid 函数的输出较为平缓,输入的变革不大时,输出的变革也不大,对于线性模型可能不够灵活。
- Sigmoid 函数的输出值在 0 到 1 之间,又可能会导致梯度爆炸的题目。
- import numpy as np
- import matplotlib.pyplot as plt
- def sigmoid(x):
- return 1.0 / (1 + np.exp(-x))
- sigmoid_inputs = np.arange(-10, 10, 0.1)
- sigmoid_outputs = sigmoid(sigmoid_inputs)
- print("Inputs: {}".format(sigmoid_inputs))
- print("Outputs: {}".format(sigmoid_outputs))
- plt.plot(sigmoid_inputs, sigmoid_outputs)
- plt.xlabel("Sigmoid Inputs")
- plt.ylabel("Sigmoid Outputs")
- plt.show()
复制代码
Tanh 函数
\(\Large tanh(x) = \frac{e^{x} - e^{-x}}{e^{x} + e^{-x}}\)
Tanh 函数将实值数压缩到 [-1, 1] 范围内。该函数是非线性的,但与 Sigmoid 不同的是,它的输出是零中心的。因此,在实践中,tanh 非线性总是优于 sigmoid 非线性。
Tanh函数优点:
- 输出均值为零:tanh函数的输出在正负方向上以原点对称,输出均值为零。这使得数据在通过网络时更容易归一化,从而加速收敛速率。
- 非线性:tanh函数引入了非线性因素,使得神经网络可以逼近任何非线性函数,从而增强了模型的表达能力。
- 梯度较大:在输入值接近零时,tanh函数的梯度较大,这有助于在反向传播过程中更有用地更新权重。
Tanh函数缺点:
- 梯度消失题目:与sigmoid函数类似,tanh函数在输入值较大或较小时,其导数趋近于零,导致梯度消失题目。这会使得网络在训练过程中难以更新权重,影响模型的学习效果。
- 盘算复杂度较高:tanh函数涉及指数运算,相对于ReLU等简单的激活函数,其盘算复杂度较高,可能会影响训练速率。
- import numpy as np
- import matplotlib.pyplot as plt
- # 生成数据
- x = np.linspace(-5, 5, 500)
- # 定义tanh函数
- tanh = np.tanh(x)
- # 绘制tanh函数图像
- plt.plot(x, tanh, label='tanh')
- plt.legend(loc='best')
- plt.xlabel('x')
- plt.ylabel('y')
- plt.xlim(-5, 5)
- plt.ylim(-1, 2)
- plt.show()
复制代码
ReLU 函数
\(\begin{split}R(x) = \begin{Bmatrix} x & x > 0 \\ 0 & x
|