小言_互联网的博客

最原始的GAN-我开始慢慢的懂GAN了

217人阅读  评论(0)

参考一篇非常全面的博文(传送门),把最原始的GAN网络过了一遍,虽然还是心中有疑虑,还是有问题,但是好事多磨,总会想明白的。

自己想不懂的问题:

1.在训练网络(generator)中,它是怎么生成一个虚假图片的?

build_generator()这个函数就是一个全连接网络,都说generator就是来生成一个虚假图片的,但是最后build_generator返回不是一个造好的虚假图片啊!

在代码部分:

  noise= np.random.normal(0,1, (batch_size, 100))
  fake_images = generator.predict(noise)

由np.random.normal函数,生成正态分布的数据。将数据传入predict函数,为输入样本生成输出预测,预测的 Numpy 数组(或数组列表)。

这个地方的fake_images,我在程序中输出看了一下,图片信息看不懂。

所以很困惑,generator生成的虚假图片,是个什么样子的?我们给出的数据集是手写数据集,生成的虚假图片不应该是数字吗?

-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

哈哈!我看懂啦!

1. fake_images的维度是(128,784)的,生成的图像是叠加在一起的,这就是我为什么看不懂生成的图片是个什么东西,因为我输出的维度不对,128是128张图片,784是28*28。(128,784)整体理解为,输出了128张28*28的图片。下面我就开始调整我输出的图像的维度了。

2.我把bach_size设置为1,这样输出的fake_images的维度就是(1,784),然后我再把生成的图片的维度转换一下,把一维的784,转换为二维的28*28

将图片转换维度后,就生成了上面的图片,这个图片就是生成器生成的图片。

-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

2.real_images = X_train[np.random.randint(0, X_train.shape[0], batch_size)]

这个是真实图像,X_train的维度是(60000,784)。np.random.randint(low,high,size,dtype)生成一个128维的行向量,行向量的数字范围是0-60000

输出的真实图像的维度是(128, 784);而且真实图像也是我所看不懂的。

为什么是这个样子的呢?

-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

解答:

1.首先,生成的real_images图片的维度是错误的,一开始的batch_size的大小是128,所以生成的real_images的维度是(128,784)。

现在,我把batch_size的大小设置为了1,维度大小为(1.784),即生成了1张一维的图片,我把一维的784转换为二维的28*28

这样就能显示出来,从训练集中选出的真实图片里的数字是多少了

-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

3.GAN.train_on_batch(noise, label_real)

这个地方的代码是在生成训练网络,让鉴别网络停止训练

向网络中输入一堆噪声,期待的输出是将假图片预测为真。

我所理解:生成的假的图片,将假的图片预测为真了,说明生成假图片的能力提升了,下面该提升的就是鉴别能力了。

生成了虚假图片和真实图片之后,还生成了图片的标签,将图片和标签一起放进鉴别器里去鉴别,来提高鉴别器的鉴别能力。

再之后是鉴别器停止训练,训练生成器, 生成的假的图片,将假的图片预测为真了,说明生成假图片的能力提升了,下面该提升的就是鉴别能力了。


  
  1. # -*- coding: utf-8 -*-
  2. """
  3. Created on Sat May 22 15:40:12 2021
  4. @author: LiMeng
  5. """
  6. from keras.datasets import mnist
  7. from keras.layers import Dense, Dropout, Input
  8. from keras.models import Model,Sequential
  9. from keras.layers.advanced_activations import LeakyReLU
  10. from keras.optimizers import Adam
  11. from tqdm import tqdm
  12. import numpy as np
  13. import matplotlib.pyplot as plt
  14. #%matplotlib inline
  15. #from google.colab import drive
  16. # Load the dataset
  17. def load_data():
  18. (x_train, y_train), (_, _) = mnist.load_data()
  19. x_train = (x_train.astype(np.float32) - 127.5)/ 127.5
  20. # Convert shape from (60000, 28, 28) to (60000, 784)
  21. x_train = x_train.reshape( 60000, 784)
  22. return (x_train, y_train)
  23. X_train, y_train = load_data()
  24. print(X_train.shape, y_train.shape)
  25. def build_generator():
  26. model = Sequential()
  27. model.add(Dense(units= 256, input_dim= 100))
  28. model.add(LeakyReLU(alpha= 0.2))
  29. model.add(Dense(units= 512))
  30. model.add(LeakyReLU(alpha= 0.2))
  31. model.add(Dense(units= 1024))
  32. model.add(LeakyReLU(alpha= 0.2))
  33. model.add(Dense(units= 784, activation= 'tanh'))
  34. model.compile(loss= 'binary_crossentropy', optimizer=Adam( 0.0002, 0.5))
  35. return model
  36. generator = build_generator()
  37. generator.summary()
  38. """
  39. dropout是指在深度学习网络的训练过程中,对于神经网络单元,按照一定的概率将其暂时从网络中丢弃。注意是暂时,对于随机梯度下降来说,由于是随机丢弃,故而每一个mini-batch都在训练不同的网络。
  40. dropout是CNN中防止过拟合提高效果的一个大杀器
  41. """
  42. def build_discriminator():
  43. model = Sequential()
  44. model.add(Dense(units= 1024 ,input_dim= 784))
  45. model.add(LeakyReLU(alpha= 0.2))
  46. model.add(Dropout( 0.3))
  47. model.add(Dense(units= 512))
  48. model.add(LeakyReLU(alpha= 0.2))
  49. model.add(Dropout( 0.3))
  50. model.add(Dense(units= 256))
  51. model.add(LeakyReLU(alpha= 0.2))
  52. model.add(Dropout( 0.3))
  53. model.add(Dense(units= 1, activation= 'sigmoid'))
  54. model.compile(loss= 'binary_crossentropy', optimizer=Adam( 0.0002, 0.5))
  55. return model
  56. discriminator = build_discriminator()
  57. discriminator.summary()
  58. def build_GAN(discriminator, generator):
  59. discriminator.trainable= False
  60. GAN_input = Input(shape=( 100,))
  61. x = generator(GAN_input)
  62. GAN_output= discriminator(x)
  63. GAN = Model(inputs=GAN_input, outputs=GAN_output)
  64. GAN.compile(loss= 'binary_crossentropy', optimizer=Adam( 0.0002, 0.5))
  65. return GAN
  66. GAN = build_GAN(discriminator, generator)
  67. GAN.summary()
  68. def draw_images(generator, epoch, examples=25, dim=(5,5), figsize=(10,10)):
  69. noise= np.random.normal(loc= 0, scale= 1, size=[examples, 100])
  70. generated_images = generator.predict(noise)
  71. generated_images = generated_images.reshape( 25, 28, 28)
  72. plt.figure(figsize=figsize)
  73. for i in range(generated_images.shape[ 0]):
  74. plt.subplot(dim[ 0], dim[ 1], i+ 1)
  75. plt.imshow(generated_images[i], interpolation= 'nearest', cmap= 'Greys')
  76. plt.axis( 'off')
  77. plt.tight_layout()
  78. plt.savefig( 'Generated_images %d.png' %epoch)
  79. def train_GAN(epochs=1, batch_size=128):
  80. #Loading the data
  81. X_train, y_train = load_data()
  82. # Creating GAN
  83. generator= build_generator()
  84. discriminator= build_discriminator()
  85. GAN = build_GAN(discriminator, generator)
  86. # print("\nepochs %d\n" %epochs)
  87. for i in range( 1, epochs+ 1):
  88. print( "\nEpoch %d\n" %i)
  89. for _ in tqdm(range(batch_size)):
  90. # Generate fake images from random noiset
  91. """
  92. np.random.normal生成正态分布:均值为0,方差为1,维度为(batch_size,100)--->(128,100)
  93. generator生成器的输入是128张100维的数据 fake_images即为generator生成的虚假图像
  94. np.random.randint(low,high,size,dtype) array = np.random.randint(0, X_train.shape[0], batch_size)
  95. 生成128维(行向量) 0-60000的数字,X_train.shape[0]为 60000,
  96. """
  97. noise= np.random.normal( 0, 1, (batch_size, 100))
  98. fake_images = generator.predict(noise)
  99. #画出虚假图像
  100. #plt.imshow(fake_images)
  101. #plt.title("fake_images")
  102. # Select a random batch of real images from MNIST
  103. real_images = X_train[np.random.randint( 0, X_train.shape[ 0], batch_size)]
  104. #画出真实图像
  105. #plt.imshow(real_images)
  106. #plt.title("real_images")
  107. # Labels for fake and real images
  108. label_fake = np.zeros(batch_size)
  109. label_real = np.ones(batch_size)
  110. # Concatenate fake and real images
  111. X = np.concatenate([fake_images, real_images])
  112. y = np.concatenate([label_fake, label_real])
  113. # Train the discriminator
  114. discriminator.trainable= True
  115. discriminator.train_on_batch(X, y)
  116. # Train the generator/chained GAN model (with frozen weights in discriminator)
  117. discriminator.trainable= False
  118. GAN.train_on_batch(noise, label_real)
  119. #Draw generated images every 15 epoches
  120. if i == 1 or i % 10 == 0:
  121. draw_images(generator, i)
  122. train_GAN(epochs= 400, batch_size= 128)

 


转载:https://blog.csdn.net/LMengi000/article/details/117168791
查看评论
* 以上用户言论只代表其个人观点,不代表本网站的观点或立场