我一直在尝试实施面书的DCGan,并且在将近两个星期内受到以下两个问题的阻挠。任何建议,将不胜感激。谢谢。
问题1:
DCGAN论文建议生成器和鉴别器都使用BN(批量归一化)。但是,使用BN不能获得比没有BN更好的结果。
我复制了我使用的DCGAN模型,该模型与DCGAN纸完全相同。我不认为这是由于过度拟合。因为(1)它始终显示与初始噪声图像相同的噪声,并且似乎从未受到过训练。 (2)损耗值非常稳定,gan和判别器都没有真正改变。 (它保持在0.6〜0.7左右,并且从未像两个模型都崩溃时一样感觉到跌落或颠簸。)如果我仅检查损失函数,则似乎训练得很好。
问题2:
当我使用float16时,它总是为Nan提供以下模型。 我将epsilon都更改为1e-4 1e-3,但是都失败了。 这是另一个问题。 如果我不使用BatchNormalization,则可以是Nan。它足够有意义,我可以理解。但是,如果我使用BatchNormalization,它将在每一层中进行标准化。即使结果变得非常大或非常小,它也会在每一层中进行批量标准化,以使结果几乎居中,并且不应发生淡出。是不是这实际上是我的想法,但我不知道我在想什么错。 请有人帮帮我。
=====生成器=====
输入#(无,128)<=潜伏
密集#(无,16384)
BatchNormalization
LeakyReLU
重塑#(无,4,4,1024)
Conv2DTranspose#(无,4,4,4,512)
BatchNormalization
LeakyReLU
Conv2DTranspose#(无,8、8、256)
BatchNormalization
LeakyReLU
Conv2DTranspose#(无,16、16、128)
BatchNormalization
LeakyReLU
Conv2DTranspose#(无,32、32、64)
BatchNormalization
LeakyReLU
Conv2DTranspose#(无,64、64、32)
BatchNormalization
LeakyReLU
Conv2DTranspose#(无,128、128、16)
BatchNormalization
LeakyReLU
Conv2D#(无,128、128、3)
=====判别器=====
Conv2D#(无,128、128、3) LeakyReLU
Conv2D#(无,64、64、16)
BatchNormalization
辍学
LeakyReLU
Conv2D#(无,32、32、32)
BatchNormalization
辍学
LeakyReLU
Conv2D#(无,16、16、64)
BatchNormalization
辍学
LeakyReLU
Conv2D#(无,8、8、128)
BatchNormalization
辍学
LeakyReLU
Conv2D#(无,4,4,4,256)
BatchNormalization
辍学
LeakyReLU
Conv2D#(无,2、2、512)
BatchNormalization
辍学
LeakyReLU
平板
辍学
密集
我尝试的最后一个超参数如下,我没有忘记在训练图像中添加高斯噪声。
image_shape => (128, 128, 3)
latent_dim => 128
channels => 3
iterations => 10000
batch_size => 128
epsilon => 0.005
weight_init_stddev => 0.02
beta_1 => 0.5
discriminator_lr => 0.0002
gan_lr => 0.0002
答案 0 :(得分:0)
我不知道DCGAN thesis的详细信息,但是如果我仔细研究,我可以找到以下指导原则来制作稳定的DCGAN。为什么在Generator中使用LeakyReLU
而不是ReLU
?
稳定的深度卷积GAN的体系结构指南
- 用跨步卷积(鉴别器)和分数跨步卷积(生成器)替换所有池化层。
- 在生成器和鉴别器中都使用batchnorm。
- 删除完全连接的隐藏层以获得更深的体系结构。
对于所有图层,- 在生成器中使用ReLU激活,除了使用Tanh的输出之外。
- 在所有层的鉴别器中使用LeakyReLU激活
答案 1 :(得分:0)
我们知道批量归一化的学习伪代码是
moving_mean = None;
moving_variance = None;
if not moving_mean:
moving_mean = current_batch_mean
else:
moving_mean = moving_mean * momentum + current_batch_mean * (1-momentum)
if not moving_variance:
moving_variance = current_batch_variance
else:
moving_variance = moving_variance * momentum + current_batch_variance * (1-momentum)
这就是重点。
tensorflow和keras的默认动量为0.99,如果您不经修改使用它,则以下更新值不会影响新的更新值。 对于火炬,默认动量为0.1,与tensorflow或keras中的0.9相同。
使用修改后的动量值,我得到了改善的结果。
如果有人像我一样遭受症状,请尝试降低动量值。
谢谢。
答案 2 :(得分:0)
在鉴别符中使用SpectralNorm
,在生成器中使用SelfModulationBatchNorm
。或者,如果您有标签,请使用ConditionalBatchNorm
。
代码,其他方法的帮助以及GAN培训here