Generative Adversarial Nets 笔记 (一)

栏目: 数据库 · 发布时间: 5年前

内容简介:GAN 的为了从训练数据中学到生成数据的概率分布 $$ P_g $$ 。 GAN 定义了一个生成函数来拟合这个分布 $$ G(z; \theta_g)$$ 这就是 GAN 的 generator 这个可以是个全连接网络,或者 CNN 网络或者其他的。 其中 $$ z $$ 是一个固定的先验概率分布,比如从特定的正太分布中采样。 判别器的作用是输入一个 样本判断是生成器生成的还是来自训练数据的真实样本。把生成器定义为 $$ D(x) $$ 我们希望最终生成器能生成更接近真实的样本,判别器也有很好的判别能力。文

Generative Adversarial Nets 笔记 (一)

GAN 的 原始论文 给出了GAN 定义和一些简单的实现。

为了从训练数据中学到生成数据的概率分布 $$ P_g $$ 。 GAN 定义了一个生成函数来拟合这个分布 $$ G(z; \theta_g)$$ 这就是 GAN 的 generator 这个可以是个全连接网络,或者 CNN 网络或者其他的。 其中 $$ z $$ 是一个固定的先验概率分布,比如从特定的正太分布中采样。 判别器的作用是输入一个 样本判断是生成器生成的还是来自训练数据的真实样本。把生成器定义为 $$ D(x) $$ 我们希望最终生成器能生成更接近真实的样本,判别器也有很好的判别能力。文中定义了如下的判别器的优化函数 Generative Adversarial Nets 笔记 (一)

对于生成器最开始的时候的 loss 太小而导致梯度饱和作者的方式是最大化 $$ log(1-D(G(x))) $$

原文从理论的角度证明了这样得到的分布是全局最优的

一个手写数字生成的例子:

import tensorflow as tf

mnist = tf.keras.datasets.mnist

(x_train, y_train),(x_test, y_test) = mnist.load_data()
IMAGE_PIXELS = 28*28
NOISE_SIZE = 100
BATCH_SIZE = 100



def noise(n_rows, n_cols):
    return np.random.normal(size=(n_rows, n_cols))

def xavier_init(size):
    in_dim = size[0] if len(size) == 1 else size[1]
    stddev = 1. / np.sqrt(float(in_dim))
    return tf.random_uniform(shape=size, minval=-stddev, maxval=stddev)

def images_to_vectors(images):
    return images.reshape(images.shape[0], IMAGE_PIXELS)

def vectors_to_images(vectors):
    return vectors.reshape(vectors.shape[0], 28, 28, 1)

X = tf.placeholder(tf.float32, shape=(None, IMAGE_PIXELS))

# Layer 1 Variables
D_W1 = tf.Variable(xavier_init([784, 1024]))
D_B1 = tf.Variable(xavier_init([1024]))

# Layer 2 Variables
D_W2 = tf.Variable(xavier_init([1024, 512]))
D_B2 = tf.Variable(xavier_init([512]))

# Layer 3 Variables
D_W3 = tf.Variable(xavier_init([512, 256]))
D_B3 = tf.Variable(xavier_init([256]))

# Out Layer Variables
D_W4 = tf.Variable(xavier_init([256, 1]))
D_B4 = tf.Variable(xavier_init([1]))

# Store Variables in list
D_var_list = [D_W1, D_B1, D_W2, D_B2, D_W3, D_B3, D_W4, D_B4]
def discriminator():
    l1 = tf.nn.dropout(tf.nn.leaky_relu(tf.matmul(x,   D_W1) + D_B1, .2), .3)
    l2 = tf.nn.dropout(tf.nn.leaky_relu(tf.matmul(l1,  D_W2) + D_B2, .2), .3)
    l3 = tf.nn.dropout(tf.nn.leaky_relu(tf.matmul(l2,  D_W3) + D_B3, .2), .3)
    out = tf.matmul(l3, D_W4) + D_B4
    return out

Z = tf.placeholder(tf.float32, shape=(None, NOISE_SIZE))

# Layer 1 Variables
G_W1 = tf.Variable(xavier_init([100, 256]))
G_B1 = tf.Variable(xavier_init([256]))

# Layer 2 Variables
G_W2 = tf.Variable(xavier_init([256, 512]))
G_B2 = tf.Variable(xavier_init([512]))

# Layer 3 Variables
G_W3 = tf.Variable(xavier_init([512, 1024]))
G_B3 = tf.Variable(xavier_init([1024]))

# Out Layer Variables
G_W4 = tf.Variable(xavier_init([1024, 784]))
G_B4 = tf.Variable(xavier_init([784]))

G_var_list = [G_W1, G_B1, G_W2, G_B2, G_W3, G_B3, G_W4, G_B4]
def generator():
    l1 = tf.nn.leaky_relu(tf.matmul(z,  G_W1) + G_B1, .2)
    l2 = tf.nn.leaky_relu(tf.matmul(l1, G_W2) + G_B2, .2)
    l3 = tf.nn.leaky_relu(tf.matmul(l2, G_W3) + G_B3, .2)
    out = tf.nn.tanh(tf.matmul(l3, G_W4) + G_B4)
    return out, var_list

G_sample = generator(Z)
D_real = discriminator(X)
D_fake = discriminator(G_sample)


# Losses
D_loss_real = tf.reduce_mean(tf.nn.sigmoid_cross_entropy_with_logits(logits=D_real, labels=tf.ones_like(D_real)))
D_loss_fake = tf.reduce_mean(tf.nn.sigmoid_cross_entropy_with_logits(logits=D_fake, labels=tf.zeros_like(D_fake)))
D_loss = D_loss_real + D_loss_fake
G_loss = tf.reduce_mean(tf.nn.sigmoid_cross_entropy_with_logits(logits=D_fake, labels=tf.ones_like(D_fake)))

# Optimizers
D_opt = tf.train.AdamOptimizer(2e-4).minimize(D_loss, var_list=D_var_list)
G_opt = tf.train.AdamOptimizer(2e-4).minimize(G_loss, var_list=G_var_list)

num_test_samples = 16
test_noise = noise(num_test_samples, NOISE_SIZE)



num_epochs = 200

# Start interactive session
session = tf.InteractiveSession()
# Init Variables
tf.global_variables_initializer().run()

for epoch in range(num_epochs):
    for n_batch, (batch,_) in enumerate(data_loader):

        # 1. Train Discriminator
        X_batch = images_to_vectors(batch.permute(0, 2, 3, 1).numpy())
        feed_dict = {X: X_batch, Z: noise(BATCH_SIZE, NOISE_SIZE)}
        _, d_error, d_pred_real, d_pred_fake = session.run(
            [D_opt, D_loss, D_real, D_fake], feed_dict=feed_dict
        )

        # 2. Train Generator
        feed_dict = {Z: noise(BATCH_SIZE, NOISE_SIZE)}
        _, g_error = session.run(
            [G_opt, G_loss], feed_dict=feed_dict
        )

        if n_batch % 100 == 0:
            display.clear_output(True)
            # Generate images from test noise
            test_images = session.run(
                G_sample, feed_dict={Z: test_noise}
            )
            test_images = vectors_to_images(test_images)
            # Log Images
            # Log Status

定义好模型和目标函数就可以用梯度更新的方式来训练模型。 看似还挺简单的和其他生成模型对比一下会发现我们不需要对数据的分布有任何的先验假设,比如 LDA 就是多项式分布的混合,而且对各个随机变量之间的关系也有很强的假设。

GAN 的特性很有意思,比如可以生成各种图像,语音文本之类的数据。我还是有几个问题记录下:

  1. 如何控制生成的类容,比如手写数字生成,生成过程中输入的是随机噪音,生成的内容就无法控制,如何生成指定的数字。
  2. GAN 模型的评价方法和其他在弱监督学习场景下的应用效果如何。

以上所述就是小编给大家介绍的《Generative Adversarial Nets 笔记 (一)》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

数据结构 Python语言描述

数据结构 Python语言描述

[美] Kenneth A. Lambert 兰伯特 / 李军 / 人民邮电出版社 / 2017-12-1 / CNY 69.00

在计算机科学中,数据结构是一门进阶性课程,概念抽象,难度较大。Python语言的语法简单,交互性强。用Python来讲解数据结构等主题,比C语言等实现起来更为容易,更为清晰。 《数据结构 Python语言描述》第1章简单介绍了Python语言的基础知识和特性。第2章到第4章对抽象数据类型、数据结构、复杂度分析、数组和线性链表结构进行了详细介绍,第5章和第6章重点介绍了面向对象设计的相关知识、......一起来看看 《数据结构 Python语言描述》 这本书的介绍吧!

CSS 压缩/解压工具
CSS 压缩/解压工具

在线压缩/解压 CSS 代码

RGB HSV 转换
RGB HSV 转换

RGB HSV 互转工具

HEX HSV 转换工具
HEX HSV 转换工具

HEX HSV 互换工具