ReLU衍生物与NumPy

Egb*_*ert 3 python arrays numpy activation-function relu

import numpy as np

def relu(z):
    return np.maximum(0,z)

def d_relu(z):
    z[z>0]=1
    z[z<=0]=0
    return z

x=np.array([5,1,-4,0])
y=relu(x)
z=d_relu(y)
print("y = {}".format(y))
print("z = {}".format(z))
Run Code Online (Sandbox Code Playgroud)

上面的代码输出:

y = [1 1 0 0]
z = [1 1 0 0]
Run Code Online (Sandbox Code Playgroud)

代替

y = [5 1 0 0]
z = [1 1 0 0]
Run Code Online (Sandbox Code Playgroud)

据我了解,我使用过的函数调用只应该按值传递,传递变量的副本。

为什么我的d_relu函数会影响y变量?

cs9*_*s95 6

您的第一个错误是假设python按值传递对象...否-而是按赋值传递(如果您熟悉此概念,则类似于按引用传递)。但是,仅顾名思义,可变对象可以就地修改。其中包括numpy数组。

您不应该就地进行d_relu修改z,因为这就是现在通过z[...] = ...语法进行的操作。尝试使用广播比较构建遮罩,然后返回该遮罩。

def d_relu(z):
    return (z > 0).astype(int)
Run Code Online (Sandbox Code Playgroud)

这将返回一个新的数组,而不是z就地进行修改,并且您的代码会打印出来

y = [5 1 0 0]
z = [1 1 0 0]
Run Code Online (Sandbox Code Playgroud)

如果您要构建分层体系结构,则可以在前向通过阶段利用计算出的蒙版:

class relu:
    def __init__(self):
        self.mask = None

    def forward(self, x):
        self.mask = x > 0
        return x * self.mask

    def backward(self, x):
        return self.mask
Run Code Online (Sandbox Code Playgroud)

如果前馈期间的输入> 0,则导数简单为1,否则为0。