Paddle 实现DCGAN

传统GAN

传统的GAN可以看我的这篇文章:Paddle 基于ANN(全连接神经网络)的GAN(生成对抗网络)实现-CSDN博客

DCGAN

DCGAN是适用于图像生成的GAN,它的特点是:

  • 只采用卷积层和转置卷积层,而不采用全连接层
  • 在每个卷积层或转置卷积层之间,插入一个批归一化层和ReLU激活函数

转置卷积层

转置卷积层执行的是转置卷积或反卷积的操作,即它是常规卷积层的反向操作。它接收一个低分辨率的输入,然后将其通过转置滤波器升采样到更高的分辨率。

对于一个卷积层,它的输出大小公式是:

o = \frac{i + 2p - k}{s} + 1

其中,o表示输出大小,i表示输入大小,p表示填充(padding),k表示卷积核大小(kernel_size),s表示步长(stride)。也就是说:输出大小 = (输入大小 - 卷积核大小 + 2 × 填充数) ÷ 步长 + 1

而对于一个转置卷积层,它的输出大小公式是:

o = s(i-1)-2p+k+u

 其中,o表示输出大小,i表示输入大小,p表示填充(padding),k表示反卷积核大小(kernel_size),s表示步长(stride),u表示输出填充(output padding)。也就是说:输出大小 = (输入大小 - 1) * 步长 - 2*填充 + 反卷积大小 + 输出填充

在paddle中,转置卷积层可以这么定义:

paddle.nn.Conv2DTranspose(in_channels, out_channels, kernel_size, stride, padding)

像卷积层一样,反卷积层的in_channels表示输入通道数(如形如(3, 32, 32)的图片张量的通道数就是3),out_channels表示输出通道数(如把(64, 32, 32)变成3通道的彩色图像(3, 32, 32))。 

代码实现

这里我们采用NWPU-RESISC45数据集,从中选择“freeway”(高速公路)作为训练数据,让机器生成高速公路的图片。这个训练数据内有700张256x256的图片,但由于我的电脑显存不足,因此将图片大小设置为64x64.

先写dataset.py:

import paddle
import numpy as np
from PIL import Image
import osdef getAllPath(path):return [os.path.join(path, f) for f in os.listdir(path)]class FreewayDataset(paddle.io.Dataset):def __init__(self, transform=None):super().__init__()self.data = []for path in getAllPath('./freeway'):img = Image.open(path)img = img.resize((64, 64))img = np.array(img, dtype=np.float32).transpose((2, 1, 0))if transform is not None:img = transform(img)self.data.append(img)self.data = np.array(self.data, dtype=np.float32)def __getitem__(self, idx):return self.data[idx]def __len__(self):return len(self.data)

然后写训练脚本:

from dataset import FreewayDataset
import paddle
from models import Generator, Discriminator
import numpy as npdataset = FreewayDataset()
dataloader = paddle.io.DataLoader(dataset, batch_size=32, shuffle=True)netG = Generator()
netD = Discriminator()if 1:try:mydict = paddle.load('generator.params')netG.set_dict(mydict)mydict = paddle.load('discriminator.params')netD.set_dict(mydict)except:print('fail to load model')loss = paddle.nn.BCELoss()optimizerD = paddle.optimizer.Adam(parameters=netD.parameters(), learning_rate=0.0002, beta1=0.5, beta2=0.999)
optimizerG = paddle.optimizer.Adam(parameters=netG.parameters(), learning_rate=0.0002, beta1=0.5, beta2=0.999)# 最大迭代epoch
max_epoch = 1000for epoch in range(max_epoch):now_step = 0for step, data in enumerate(dataloader):############################# (1) 更新鉴别器############################ 清除D的梯度optimizerD.clear_grad()# 传入正样本,并更新梯度pos_img = datalabel = paddle.full([pos_img.shape[0], 1, 1, 1], 1, dtype='float32')pre = netD(pos_img)loss_D_1 = loss(pre, label)loss_D_1.backward()# 通过randn构造随机数,制造负样本,并传入D,更新梯度noise = paddle.randn([pos_img.shape[0], 100, 1, 1], 'float32')neg_img = netG(noise)label = paddle.full([pos_img.shape[0], 1, 1, 1], 0, dtype='float32')pre = netD(neg_img.detach())  # 通过detach阻断网络梯度传播,不影响G的梯度计算loss_D_2 = loss(pre, label)loss_D_2.backward()# 更新D网络参数optimizerD.step()optimizerD.clear_grad()loss_D = loss_D_1 + loss_D_2############################# (2) 更新生成器############################ 清除D的梯度optimizerG.clear_grad()noise = paddle.randn([pos_img.shape[0], 100, 1, 1], 'float32')fake = netG(noise)label = paddle.full((pos_img.shape[0], 1, 1, 1), 1, dtype=np.float32, )output = netD(fake)# 这个写法没有问题,因为这个loss既会影响到netG(output=netD(netG(noise)))的梯度,也会影响到netD的梯度,但是之后的代码并没有更新netD的参数,而循环开头就清除了netD的梯度loss_G = loss(output, label)loss_G.backward()# 更新G网络参数optimizerG.step()optimizerG.clear_grad()now_step += 1############################ 输出日志###########################if now_step % 10 == 0:print(f'Epoch ID={epoch} Batch ID={now_step} \n\n D-Loss={float(loss_D)} G-Loss={float(loss_G)}')paddle.save(netG.state_dict(), "generator.params")
paddle.save(netD.state_dict(), "discriminator.params")

 最后编写图片生成脚本:

import paddle
from models import Generator
import matplotlib.pyplot as plt# 加载模型
netG = Generator()
mydict = paddle.load('generator.params')
netG.set_dict(mydict)# 设置matplotlib的显示环境
fig, axs = plt.subplots(nrows=2, ncols=5, figsize=(15, 6))  # 创建一个2x5的子图网格# 生成10个噪声向量
for i, ax in enumerate(axs.flatten()):noise = paddle.randn([1, 100, 1, 1], 'float32')img = netG(noise)img = img.numpy()[0].transpose((2, 1, 0))  # img.numpy():张量转np数组img[img < 0] = 0  # 将img中所有小于0的元素赋值为0# 显示图片ax.imshow(img)ax.axis('off')  # 不显示坐标轴# 显示图像
plt.show()

经过数次训练,最终的效果如下:

这样看来,至少有点高速公路的感觉了。 

参考

通过DCGAN实现人脸图像生成-使用文档-PaddlePaddle深度学习平台

卷积层和反卷积层输出特征图大小计算_输出特征图大小的计算方法-CSDN博客 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/10128.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

nvm切换node版本命令

nvm切换node版本命令 使用 nvm 切换 Node.js 版本的命令如下&#xff1a;12 查看 nvm 支持安装的 Node 版本。进入命令行界面&#xff0c;输入 nvm list available&#xff0c;这会显示可以安装的 Node.js 版本。安装指定版本的 Node.js。输入 nvm install <版本号>&…

优先队列——大小堆—— priority_queue

本人博客主页 本篇博客相关博客 二叉树--讲解 文章目录 目录 文章目录 前言 一、priority_queue是什么&#xff1f; 二、priority_queue的使用 1、相关函数 2、代码使用 3、堆的插入删除 三、模拟实现 1、大框架 2、仿函数 3、向下调整 4、向下调整 总结 前言 在我们学习二叉…

免费SSL证书怎么签发

大家都知道SSL证书好&#xff0c;作用大&#xff0c;安全性高&#xff0c;能加权重&#xff0c;等保必须的参考值。但是如何选择合适且正确的证书也是至关重要的&#xff0c;网站更适合单域名证书、多域名证书、泛域名证书、还是多域名通配符证书。 首先大家要清楚&#xff0c…

网站访问提示不安全怎么办??

当网站访问时提示“不安全”&#xff0c;这通常与网站的SSL证书有关&#xff0c;或者是网站本身存在一些安全风险。以下是一些解决步骤和建议&#xff1a; 1、检查URL前缀&#xff1a;首先&#xff0c;检查URL是否以https://开头。如果仍然是http://&#xff0c;则网站没有使用…

python 新特性

文章目录 formatted字符串字面值formatted字符串支持 字符串新方法变量类型标注二进制表示中数字为1的数量统计字典的三个方法新增mapping属性函数zip()新增strict参数dataclass字典合并match 语法 formatted字符串字面值 formatted字符串是带有’f’字符前缀的字符串&#xf…

HashMap在JDK1.8的优化

目录 数据结构上的优化 Hash碰撞问题解决方案的优化 Hash值算法的优化

我必须要吹一波MATLAB 2024a,太牛逼了!|福利:附安装教程及下载地址

最近逛MATLAB官网&#xff0c;发现MATLAB 2024a版本已经Pre-release了&#xff0c;翻了下release note&#xff0c;不得不感叹&#xff0c;实在是太强了&#xff01; 这次重点更新了四个工具箱&#xff1a; Computer Vision Toolbox Deep Learning Toolbox Instrument Contro…

图像下载的新趋势:Kotlin技术探索与实践

随着互联网的迅速发展和智能设备的普及&#xff0c;图像下载作为一项重要的技术应用&#xff0c;也在不断演进和创新。在这篇文章中&#xff0c;我们将探讨图像下载的新趋势&#xff0c;并使用Kotlin语言进行实践探索。 引言 图像下载是指从网络上获取图像并保存到本地设备的…

鸿蒙内核源码分析(文件句柄篇) | 你为什么叫句柄

句柄 | handle int open(const char* pathname,int flags); ssize_t read(int fd, void *buf, size_t count); ssize_t write(int fd, const void *buf, size_t count); int close(int fd);只要写过应用程序代码操作过文件不会陌生这几个函数,文件操作的几个关键步骤嘛,跟把大…

HashMap扩容机制

HashMap数组的初始容量16和负载因子为0.75。当HashMap中元素个数超过负载因子loadFactor时就会触发扩容,loadFactor默认大小为0.75,默认情况下数组大小为16,当hashmap中元素个数超过16 * 0.75 = 12时,数组的大小扩展为2 * 16=32 即扩大一倍,新建一个扩容后大小的数组,然后…

《intel开发手册卷1》学习笔记3

1、数据传输指令 MOV 指令在内存和处理器寄存器之间执行基本的加载数据和存储数据操作&#xff0c;并在寄存器之间执行数据移动操作。MOV 指令不能将数据从一个内存位置移动到另一个内存位置&#xff0c;也不能将数据从一个段寄存器移动到另一个段寄存器。内存到内存的移动使用…

通过wget下载ftp文件

通过wget下载ftp文件 基础用法带密码的http文件带密码的ftp文件补充 基础用法 在下载的过程中会显示进度条&#xff0c;包含百分比&#xff0c;已下载字节&#xff0c;下载速度&#xff0c;剩余时间。 # 下载单个文件 wget [url_file]# 下载目录全部文件 wget [url_dir/*] wg…

Linux开发--Bootloader应用分析

Bootloader应用分析 一个嵌入式 Linux 系统从软件的角度看通常可以分为四个层次&#xff1a; 引导加载程序。包括固化在固件( firmware )中的 boot 代码(可选)&#xff0c;和 Boot Loader 两大部分。 Linux 内核。特定于嵌入式板子的定制内核以及内核的启动参数。 文件系统…

H264 SP帧等知识笔记

H.264是一种广泛使用的视频编码标准&#xff0c;它使用多种类型的帧来实现高效的视频压缩。在H.264中&#xff0c;参考帧和重建帧是两个重要的概念&#xff0c;它们之间既有区别又有联系。 参考帧&#xff1a; 参考帧是用于预测其他帧的帧。在H.264中&#xff0c;编码器会利用…

大华智能物联综合管理平台 fastjson远程代码执行漏洞复现

0x01 产品简介 大华ICC智能物联综合管理平台对技术组件进行模块化和松耦合,将解决方案分层分级,提高面向智慧物联的数据接入与生态合作能力。 0x02 漏洞概述 由于大华智能物联综合管理平台使用了存在漏洞的FastJson组件,未经身份验证的攻击者可利用 /evo-runs/v1.0/auths/…

解释Java中的注解(Annotations)及其用途

Java 注解&#xff08;Annotations&#xff09;是从 Java 5 开始引入的一种元数据形式&#xff0c;它提供了一种将额外信息&#xff08;metadata&#xff09;与代码&#xff08;类、方法、变量等&#xff09;相关联的方法。注解不直接影响代码的操作&#xff0c;但可被编译器、…

【Qt】界面定制艺术:光标(cursor)、字体(font)、提示(toolTip)、焦点(focusPolicy)与样式表(styleSheet)的深度探索

文章目录 前言&#xff1a;1. cursor: 设置按钮的光标2. front&#xff1a;设置字体3. toolTip: 鼠标悬停提示4. focusPolicy&#xff1a;设置控件获取到焦点的策略5. styleSheet : 样式表总结&#xff1a; 前言&#xff1a; 在现代软件开发中&#xff0c;用户界面(UI)的设计和…

【MySQL 数据宝典】【事务锁】- 002 事务控制的演进

一、事务处理思路 1.1 排队 排队处理是事务管理最简单的方法&#xff0c;就是完全顺序执行所有事务的数据库操作&#xff0c;不需要加锁&#xff0c;简单的说就是全局排队。序列化执行所有的事务单元&#xff0c;数据库某个时刻只处理一个事务操作&#xff0c;特点是强一致性…

Java刷题-基础篇

目录 题目1&#xff1a;打印1~100内奇数和、偶数和 题目2&#xff1a;计算5的阶乘 题目3&#xff1a;计算 1!2!3!4!5! 的和 题目4&#xff1a;找1~100之间即能被3整除&#xff0c;又能被5整除的数字&#xff0c;要求必须使用break/continue 题目5&#xff1a;实现猜数字小…

LeetCode 112. 路径总和 || LeetCode 113. 路径总和ii

LeetCode 112. 路径总和 1、题目 题目链接&#xff1a;112. 路径总和 给你二叉树的根节点 root 和一个表示目标和的整数 targetSum 。判断该树中是否存在 根节点到叶子节点 的路径&#xff0c;这条路径上所有节点值相加等于目标和 targetSum 。如果存在&#xff0c;返回 true…