首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Tf 2.0 : RuntimeError: GradientTape.gradient只能在非持久性磁带上调用一次

Tf 2.0 : RuntimeError: GradientTape.gradient只能在非持久性磁带上调用一次
EN

Stack Overflow用户
提问于 2019-05-10 15:20:31
回答 2查看 8.1K关注 0票数 17

在tf 2.0 DC Gan示例中

tensorflow 2.0指南

,有两个梯度磁带。请参见下面的内容。

代码语言:javascript
复制
@tf.function
def train_step(images):
    noise = tf.random.normal([BATCH_SIZE, noise_dim])

    with tf.GradientTape() as gen_tape, tf.GradientTape() as disc_tape:
      generated_images = generator(noise, training=True)

      real_output = discriminator(images, training=True)
      fake_output = discriminator(generated_images, training=True)

      gen_loss = generator_loss(fake_output)
      disc_loss = discriminator_loss(real_output, fake_output)

    gradients_of_generator = gen_tape.gradient(gen_loss, generator.trainable_variables)
    gradients_of_discriminator = disc_tape.gradient(disc_loss, discriminator.trainable_variables)

    generator_optimizer.apply_gradients(zip(gradients_of_generator, generator.trainable_variables))
    discriminator_optimizer.apply_gradients(zip(gradients_of_discriminator, discriminator.trainable_variables))

正如你可以清楚地看到,有两个梯度磁带。我想知道使用一盘磁带会有什么不同,并将其更改为以下内容

代码语言:javascript
复制
@tf.function
def train_step(images):
    noise = tf.random.normal([BATCH_SIZE, noise_dim])

    with tf.GradientTape() as tape:
      generated_images = generator(noise, training=True)

      real_output = discriminator(images, training=True)
      fake_output = discriminator(generated_images, training=True)

      gen_loss = generator_loss(fake_output)
      disc_loss = discriminator_loss(real_output, fake_output)

    gradients_of_generator = tape.gradient(gen_loss, generator.trainable_variables)
    gradients_of_discriminator = tape.gradient(disc_loss, discriminator.trainable_variables)

    generator_optimizer.apply_gradients(zip(gradients_of_generator, generator.trainable_variables))
    discriminator_optimizer.apply_gradients(zip(gradients_of_discriminator, discriminator.trainable_variables))

这会给我以下错误:

代码语言:javascript
复制
RuntimeError: GradientTape.gradient can only be called once on non-persistent tapes.

我想知道为什么需要两盘磁带。到目前为止,关于tf2.0API的文档还很少。有没有人能给我解释或者给我指给我正确的文档/教程?

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2019-05-10 16:44:10

文档

默认情况下,只要调用GradientTape.gradient()方法,就会释放GradientTape持有的资源。要在同一计算中计算多个渐变,请创建一个持久的渐变带。这允许在对磁带对象进行垃圾回收时释放资源时多次调用gradient()方法。

可以使用以下命令创建持久渐变

并且可以/应该使用以下命令手动删除

(致谢@zwep,@Crispy13)。

票数 17
EN

Stack Overflow用户

发布于 2019-05-10 17:17:09

技术原因是

被调用两次,这在(非持久性)磁带上是不允许的。

然而,在目前的情况下,潜在的原因是GANS的训练通常是通过交替优化生成器和鉴别器来完成的。每种优化都有自己的优化器,这些优化器通常在不同的变量上运行,现在即使是最小化的损失也是不同的(

在您的代码中)。

所以你最终得到了两个梯度,因为训练GANs本质上是以交替的方式优化两个不同的(对抗性)问题。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/56072634

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档