主要内容

dlgradient

使用自动微分为自定义训练循环计算梯度

描述

使用dlgradient使用自定义训练循环的自动微分来计算导数。

提示

对于大多数深度学习任务,您可以使用预先训练的网络,并使其适应您自己的数据。有关如何使用迁移学习来重新训练卷积神经网络来对一组新图像进行分类的示例,请参见训练深度学习网络对新图像进行分类.或者,您可以使用从头开始创建和培训网络layerGraph的对象trainNetworktrainingOptions功能。

如果trainingOptions函数不提供任务所需的训练选项,则可以使用自动区分创建自定义训练循环。想要了解更多,请看为自定义训练循环定义深度学习网络

例子

dydx1,…,dydxk) = dlgradient (yx1,…,xk返回的梯度y关于变量x1通过xk

调用dlgradient从函数内部传递给dlfeval.看到使用自动微分计算梯度在深度学习工具箱中使用自动区分

dydx1,…,dydxk) = dlgradient (yx1,…,xk名称,值返回渐变并使用一个或多个名称-值对指定其他选项。例如,就要= dlgradient (y, x, RetainData,真的)使梯度保留中间值以供后续重用dlgradient调用。这种语法可以节省时间,但会占用更多内存。有关更多信息,请参见提示

例子

全部折叠

罗森布罗克函数是优化的标准测试函数。的rosenbrock.m辅助函数计算函数值,并使用自动微分来计算其梯度。

类型rosenbrock.m
函数[y,就要]=。(x) y = 100 * (x - x(1)(2)。^ 2)。²+ (1 - x(1))²;就要= dlgradient (y、x);结束

求罗森布罗克函数及其在该点处的梯度[1,2],创建一个dlarray的点,然后调用dlfeval在函数句柄上@rosenbrock

x0 = dlarray ([1, 2]);[fval, gradval] = dlfeval (x0 @rosenbrock)
Fval = 1x1 dlarray 104
梯度= 1x2 dlarray 396 200

或者,将罗森布罗克函数定义为两个输入的函数,x1和x2

类型rosenbrock2.m
函数[y,dydx1,dydx2] = rosenbrock2(x1,x2) y = 100*(x2 - x1.^2)²+ (1 - x1)²;[dydx1, dydx2] = dlgradient (y, x1, x2);结束

调用dlfeval评估rosenbrock2在两个dlarray表示输入的参数12

x1 = dlarray (1);x2 = dlarray (2);[fval, dydx1 dydx2] = dlfeval (@rosenbrock2 (x1, x2)
Fval = 1x1 dlarray 104
Dydx1 = 1x1美元396
Dydx2 = 1x1 dlarray 200

绘制罗森布罗克函数在单位平方上几个点的梯度。首先,初始化表示求值点的数组和函数的输出。

[X1 X2] = meshgrid(linspace(0,1,10));X1 = dlarray (X1 (:));X2 = dlarray (X2 (:));Y = dlarray(0(大小(X1)));DYDX1 = Y;DYDX2 = Y;

在循环中对函数求值。用以下方法绘制结果箭袋

i = 1:长度(X1) [Y (i), DYDX1(我),DYDX2 (i)) = dlfeval (@rosenbrock2, X1 (i), X2(我));结束箭袋(extractdata (X1)、extractdata (X2)、extractdata (DYDX1) extractdata (DYDX2))包含(x1的) ylabel (“x2”

图中包含一个轴对象。轴对象包含一个类型为箭筒的对象。

使用dlgradientdlfeval计算包含复数的函数的值和梯度。您可以计算复杂的梯度,或仅将梯度限制为实数。

定义的函数complexFun,列在本例的最后。这个函数实现了以下复杂的公式:

f x 2 + 3. x

定义的函数gradFun,列在本例的最后。这个函数调用complexFun并使用dlgradient来计算结果相对于输入的梯度。对于自动微分,要微分的值——即从输入计算出的函数的值——必须是一个实标量,因此该函数在计算梯度之前取结果的实部之和。函数返回函数值的实部和梯度,这可能是复杂的。

定义复平面上-2和-2之间的采样点 和2 和转换dlarray

functionRes = linspace (2100);x = function .';x = dlarray (x);

计算每个采样点的函数值和梯度。

[y, grad] = dlfeval(@gradFun,x);y = extractdata (y);

定义显示渐变的采样点。

gradientRes = linspace (2, 2, 11);xGrad = gradientRes + 1i*gradientRes.';

在这些采样点提取梯度值。

[~, gradPlot] = dlfeval (@gradFun dlarray (xGrad));gradPlot = extractdata (gradPlot);

策划的结果。使用显示亮度图像来表示函数在复平面上的值。使用箭袋表示梯度的方向和大小。

显示亮度图像((2,2),(2,2),y);轴xycolorbar举行箭袋(真实(xGrad),图像放大(xGrad),真正的(gradPlot),图像放大(gradPlot),“k”);包含(“真正的”) ylabel (“虚”)标题(“实值与梯度”"Re$(f(x)) = $ Re$((2+3i)x)$"“翻译”“乳胶”

图中包含一个轴对象。标题为实值和梯度的轴对象包含2个类型为image, quiver的对象。

函数的梯度在整个复平面上都是一样的。提取自动差分计算出的梯度值。

研究生(1,1)
Ans = 1x1 dlarray 2.000 - 3.0000i

经检验,该函数的复导数是有值的

df x dx 2 + 3.

但是,函数Re( f x )不是解析的,因此没有复导数的定义。对于MATLAB中的自动微分,微分值必须是实数,因此函数永远不能是复解析函数。相反,导数的计算使得返回的梯度指向最陡的上升方向,如图所示。这是通过解释函数Re来实现的 f x C R作为一个功能 f x R + x R × R R

函数y = (2+3i)*x;结束函数[y,grad] = gradFun(x) y = complexFun(x);y =真正的(y);研究生= dlgradient(总和(y,“所有”), x);结束

输入参数

全部折叠

要区分的变量,指定为标量dlarray对象。分化,y一定是一个跟踪函数dlarray输入(见追踪dlarray),并且必须包含支持的函数金宝appdlarray(见支持dlarray的函数列表金宝app).

要区分的变量必须是实数,即使在name-value选项中“AllowComplex”被设置为真正的

例子:100 * (x - x(1)(2)。^ 2)。²+ (1 - x(1))²

例子:relu (X)

数据类型:||逻辑

变量,指定为dlarray对象、单元格数组、结构或包含的表dlarray对象,或此类参数的任何递归组合。例如,一个参数可以是一个单元格数组,该单元格数组包含一个结构dlarray对象。

如果您指定x1,…,xk作为一个表,表必须包含以下变量:

  • —层名,指定为字符串标量。

  • 参数-参数名称,指定为字符串标量。

  • 价值—parameter的值,指定为包含a的单元格数组dlarray

例子:dlarray ([1 2; 3 4])

数据类型:||逻辑|结构体|细胞
复数的支持:金宝app是的

名称-值参数

指定可选的逗号分隔的对名称,值参数。的名字参数名和价值为对应值。的名字必须出现在引号内。可以以任意顺序指定多个名称和值对参数Name1, Value1,…,的家

例子:就要= dlgradient (y, x, RetainData,真的)使梯度保留中间值以供后续重用dlgradient调用

标记以在函数调用期间保留跟踪数据,指定为真正的.当这个论点是,一个dlarray在计算导数后立即丢弃导数轨迹。当这个论点是真正的,一个dlarray保持导数跟踪直到dlfeval函数的调用dlgradient.的真正的设置仅当dlfeval调用包含多个dlgradient调用。的真正的设置使软件使用更多的内存,但可以节省时间时,多个dlgradient调用至少使用同一跟踪的一部分。

“EnableHigherDerivatives”真正的,则中间值被保留“RetainData”期权没有效果。

例子:就要= dlgradient (y, x, RetainData,真的)

数据类型:逻辑

启用高阶导数的标志,指定为以下之一:

  • 真正的-启用高阶导数。跟踪向后传递,以便返回的梯度可用于后续调用的进一步计算dlgradient函数。如果“EnableHigherDerivatives”真正的,则中间值被保留“RetainData”期权没有效果。

  • -禁用高阶导数。不要追踪反向传递。当您只需要计算一阶导数时,使用此选项,因为这通常更快,需要更少的内存。

当使用dlgradient函数在一个AcceleratedFunction对象时,默认值为真正的.否则,默认值为

有关如何训练需要计算高阶导数的模型的示例,请参见:

数据类型:逻辑

允许在函数和复杂梯度中使用复杂变量的标志,指定为下列之一:

  • 真正的-允许在函数和复杂梯度中使用复杂变量。函数中的变量可以指定为复数。即使所有变量都是实数,梯度也可能是复杂的。求导变量必须是实数。

  • -不允许复杂变量和梯度。变量,函数中的任何变量都必须是实数。梯度总是实数。中间值仍然是复杂的。

要区分的变量必须是实数,即使在name-value选项中“AllowComplex”被设置为真正的

数据类型:逻辑

输出参数

全部折叠

梯度,返回为dlarray对象,或单元格数组、结构或包含的表dlarray对象,或此类参数的任何递归组合。的大小和数据类型dydx1,…,dydxk是否与相关的输入变量相同x1,…,xk

限制

  • dlgradient函数在使用时不支持计算高阶导数金宝appdlnetwork对象,该对象包含带有自定义向后函数的自定义层。

  • dlgradient函数在使用时不支持计算高阶导数金宝appdlnetwork对象包含以下层:

    • gruLayer

    • lstmLayer

    • bilstmLayer

  • dlgradient函数不支持计算依赖于以下函数的高阶导金宝app数:

    • 格勒乌

    • lstm

    • 嵌入

    • 刺激

    • interp1

更多关于

全部折叠

追踪dlarray

在函数的计算过程中,adlarray内部记录在a中采取的步骤跟踪,使反向模式自动区分。跟踪发生在dlfeval调用。看到自动分化背景

提示

  • 一个dlgradient调用必须在函数内部。要获得梯度的数值,必须使用dlfeval,函数的实参必须是dlarray.看到在深度学习工具箱中使用自动区分

  • 要正确评估梯度,请使用y参数必须仅使用支持的函数金宝appdlarray.看到支持dlarray的函数列表金宝app

  • 如果你设置“RetainData”的名称-值对参数真正的,该软件将在dlfeval函数调用,而不是在导数计算之后立即删除跟踪。这种保存可能导致后续的dlgradient在同一范围内调用dlfeval调用的执行速度更快,但使用的内存更多。例如,在训练一个对抗网络时“RetainData”设置是有用的,因为两个网络在训练期间共享数据和功能。看到训练生成对抗网络(GAN)

  • 当你只需要计算一阶导数时,确保“EnableHigherDerivatives”选择是因为这通常更快,需要更少的内存。

  • 复杂梯度计算使用Wirtinger导数。梯度定义为函数实部的递增方向,以求导。这是因为微分的变量——例如损失——必须是实数,即使函数是复杂的。

扩展功能

介绍了R2019b