生成对抗网络入门案例

前言

生成对抗网络(Generative Adversarial Networks,简称GANs)是一种用于生成新样本的机器学习模型。它由两个主要组件组成:生成器(Generator)和判别器(Discriminator)。生成器尝试生成与训练数据相似的新样本,而判别器则试图区分生成器生成的样本和真实训练数据。

下面是一个简单的对抗生成网络的入门例子,用于生成手写数字图像:

实现过程

1、导入必要的库和模块

python 复制代码
import numpy as np
import matplotlib.pyplot as plt
from tensorflow.keras.datasets import mnist
from tensorflow.keras.models import Sequential
from tensorflow.keras.layers import Dense, Flatten, Reshape
from tensorflow.keras.layers import Conv2D, Conv2DTranspose
from tensorflow.keras.optimizers import Adam

2、加载MNIST数据集

python 复制代码
(x_train, _), (_, _) = mnist.load_data()
x_train = x_train / 255.0
x_train = np.expand_dims(x_train, axis=3)

3、定义生成器模型

python 复制代码
generator = Sequential()
generator.add(Dense(7*7*128, input_shape=(100,), activation='relu'))
generator.add(Reshape((7, 7, 128)))
generator.add(Conv2DTranspose(64, (3, 3), strides=(2, 2), padding='same', activation='relu'))
generator.add(Conv2DTranspose(1, (3, 3), strides=(2, 2), padding='same', activation='sigmoid'))

4、定义判别器模型

python 复制代码
discriminator = Sequential()
discriminator.add(Conv2D(64, (3, 3), strides=(2, 2), padding='same', input_shape=(28, 28, 1), activation='relu'))
discriminator.add(Conv2D(128, (3, 3), strides=(2, 2), padding='same', activation='relu'))
discriminator.add(Flatten())
discriminator.add(Dense(1, activation='sigmoid'))

5、编译判别器模型

python 复制代码
discriminator.compile(loss='binary_crossentropy', optimizer=Adam(learning_rate=0.0002, beta_1=0.5), metrics=['accuracy'])

6、冻结判别器模型的权重

python 复制代码
discriminator.trainable = False

7、定义GAN模型

python 复制代码
gan = Sequential()
gan.add(generator)
gan.add(discriminator)

8、编译GAN模型

python 复制代码
gan.compile(loss='binary_crossentropy', optimizer=Adam(learning_rate=0.0002, beta_1=0.5))

9、定义训练函数

python 复制代码
def train_gan(epochs, batch_size, sample_interval):
    for epoch in range(epochs):
        # 生成随机噪声作为输入
        noise = np.random.normal(0, 1, (batch_size, 100))
        
        # 生成假样本
        generated_images = generator.predict(noise)
        
        # 从真实样本中随机选择一批样本
        real_images = x_train[np.random.randint(0, x_train.shape[0], batch_size)]
        
        # 训练判别器
        discriminator_loss_real = discriminator.train_on_batch(real_images, np.ones((batch_size, 1)))
        discriminator_loss_fake = discriminator.train_on_batch(generated_images, np.zeros((batch_size, 1)))
        discriminator_loss = 0.5 * np.add(discriminator_loss_real, discriminator_loss_fake)
        
        # 训练生成器
        noise = np.random.normal(0, 1, (batch_size, 100))
        generator_loss = gan.train_on_batch(noise, np.ones((batch_size, 1)))
        
        # 打印损失
        if epoch % sample_interval == 0:
            print(f"Epoch {epoch}/{epochs}, Discriminator Loss: {discriminator_loss[0]}, Generator Loss: {generator_loss}")
            
            # 保存生成的图像
            save_images(epoch)

10、保存生成的图像

python 复制代码
def save_images(epoch):
    rows, cols = 5, 5
    noise = np.random.normal(0, 1, (rows * cols, 100))
    generated_images = generator.predict(noise)
    generated_images = 0.5 * generated_images + 0.5
    fig, axs = plt.subplots(rows, cols)
    idx = 0
    for i in range(rows):
        for j in range(cols):
            axs[i, j].imshow(generated_images[idx, :, :, 0], cmap='gray')
            axs[i, j].axis('off')
            idx += 1
    fig.savefig(f"gan_images/mnist_{epoch}.png")
    plt.close()

11、训练GAN模型

python 复制代码
epochs = 10000
batch_size = 128
sample_interval = 1000

完整代码

python 复制代码
import numpy as np
import matplotlib.pyplot as plt
from tensorflow.keras.datasets import mnist
from tensorflow.keras.models import Sequential
from tensorflow.keras.layers import Dense, Flatten, Reshape
from tensorflow.keras.layers import Conv2D, Conv2DTranspose
from tensorflow.keras.optimizers import Adam

# 加载MNIST数据集
(x_train, _), (_, _) = mnist.load_data()
x_train = x_train / 255.0
x_train = np.expand_dims(x_train, axis=3)

# 定义生成器模型
generator = Sequential()
generator.add(Dense(7*7*128, input_shape=(100,), activation='relu'))
generator.add(Reshape((7, 7, 128)))
generator.add(Conv2DTranspose(64, (3, 3), strides=(2, 2), padding='same', activation='relu'))
generator.add(Conv2DTranspose(1, (3, 3), strides=(2, 2), padding='same', activation='sigmoid'))

# 定义判别器模型
discriminator = Sequential()
discriminator.add(Conv2D(64, (3, 3), strides=(2, 2), padding='same', input_shape=(28, 28, 1), activation='relu'))
discriminator.add(Conv2D(128, (3, 3), strides=(2, 2), padding='same', activation='relu'))
discriminator.add(Flatten())
discriminator.add(Dense(1, activation='sigmoid'))

# 编译判别器模型
discriminator.compile(loss='binary_crossentropy', optimizer=Adam(learning_rate=0.0002, beta_1=0.5), metrics=['accuracy'])

# 冻结判别器模型的权重
discriminator.trainable = False

# 定义GAN模型
gan = Sequential()
gan.add(generator)
gan.add(discriminator)

# 编译GAN模型
gan.compile(loss='binary_crossentropy', optimizer=Adam(learning_rate=0.0002, beta_1=0.5))

# 定义训练函数
def train_gan(epochs, batch_size, sample_interval):
    for epoch in range(epochs):
        # 生成随机噪声作为输入
        noise = np.random.normal(0, 1, (batch_size, 100))
        
        # 生成假样本
        generated_images = generator.predict(noise)
        
        # 从真实样本中随机选择一批样本
        real_images = x_train[np.random.randint(0, x_train.shape[0], batch_size)]
        
        # 训练判别器
        discriminator_loss_real = discriminator.train_on_batch(real_images, np.ones((batch_size, 1)))
        discriminator_loss_fake = discriminator.train_on_batch(generated_images, np.zeros((batch_size, 1)))
        discriminator_loss = 0.5 * np.add(discriminator_loss_real, discriminator_loss_fake)
        
        # 训练生成器
        noise = np.random.normal(0, 1, (batch_size, 100))
        generator_loss = gan.train_on_batch(noise, np.ones((batch_size, 1)))
        
        # 打印损失
        if epoch % sample_interval == 0:
            print(f"Epoch {epoch}/{epochs}, Discriminator Loss: {discriminator_loss[0]}, Generator Loss: {generator_loss}")
            
            # 保存生成的图像
            save_images(epoch)
            
# 保存生成的图像
def save_images(epoch):
    rows, cols = 5, 5
    noise = np.random.normal(0, 1, (rows * cols, 100))
    generated_images = generator.predict(noise)
    generated_images = 0.5 * generated_images + 0.5
    fig, axs = plt.subplots(rows, cols)
    idx = 0
    for i in range(rows):
        for j in range(cols):
            axs[i, j].imshow(generated_images[idx, :, :, 0], cmap='gray')
            axs[i, j].axis('off')
            idx += 1
    fig.savefig(f"gan_images/mnist_{epoch}.png")
    plt.close()
    
# 训练GAN模型
epochs = 10000
batch_size = 128
sample_interval = 1000

train_gan(epochs, batch_size, sample_interval)

这个例子使用了MNIST数据集,生成手写数字图像。生成器和判别器模型使用了卷积神经网络的结构。在训练过程中,生成器试图生成逼真的手写数字图像,而判别器则试图区分真实图像和生成图像。通过反复迭代训练生成器和判别器,GAN模型能够逐渐生成更逼真的手写数字图像。生成的图像会保存在gan_images文件夹中。

相关推荐
Database_Cool_1 分钟前
数据库慢查询优化首选方案:阿里云 RDS 性能洞察+自动诊断
数据库·人工智能·阿里云
2601_951659992 分钟前
YOLOv11 改进 - 主干网络 ConvNeXtV2全卷积掩码自编码器网络:轻量级纯卷积架构破解特征坍塌难题,提升特征多样性
深度学习·yolo·计算机视觉
北邮刘老师10 分钟前
国标配套开源实现再升级!AIP智能体互联开源项目v2.1.0正式发布
人工智能·开源·大模型·智能体·智能体互联网
zhoupenghui16812 分钟前
【AI大模型应用开发】【项目实战】13.RAG智慧问答项目-(一)项目介绍&项目架构&项目环境配置
人工智能·docker·ai·milvus·rag·attu·rag智慧问答项目
神奇小汤圆21 分钟前
AI Coding 不只靠 Prompt:Agent 工程闭环如何接入 DevOps
人工智能
hongmai66688824 分钟前
ESP32-S2-MINI-2U-N4R2:一款为灵活部署而生的Wi-Fi MCU模组
人工智能·单片机·嵌入式硬件·物联网·智能家居
神奇小汤圆27 分钟前
AI Agent 替你写代码没问题,但这 3 类后端任务让它当场翻车
人工智能
lyy-独立开发者1 小时前
主动推理-人工海马
人工智能
云栖梦泽在1 小时前
Claude Code / Codex 使用卡顿怎么办?AI 编程 Agent 连接失败与网络排查思路
网络·人工智能·网络协议·chatgpt·性能优化
凡泰AI1 小时前
从个人用AI到企业用AI,如何为企业部署一套私有化Agent智能体运行时,将AI变成企业的基础设施
人工智能·ai·架构·agent·cio