【Python图像超分】Real-ESRGAN图像超分模型(超分辨率重建)详细安装和使用教程

1 前言

        图像超分是一种图像处理技术,旨在提高图像的分辨率,使其具有更高的清晰度和细节。这一技术通常用于图像重建、图像恢复、图像增强等领域,可以帮助我们更好地理解和利用图像信息。图像超分技术可以通过多种方法实现,包括插值算法、深度学习等。其中,深度学习的方法在近年来得到了广泛的关注和应用。基于深度学习的图像超分技术,可以利用深度神经网络学习图像的高频部分,从而提高了图像的分辨率和清晰度。

        目前应用较多的应用场景是图像及视频分辨率提高,比如可以提高以往影视作品或图像的分辨率,提高视觉感官效果;或是解决视频经有损压缩后导致视频效果退化问题。今天给大家介绍一下腾讯ARC实验室发布的一个图像超分辨率模型Real-ESRGAN:项目开源地址,论文地址。

1.1 项目效果展示

2 Python代码使用教程

2.1 依赖库安装

  • Python >= 3.7 (推荐使用Anaconda或Miniconda)
  • PyTorch >= 1.7
  • 这里比较推荐大家用离线本地安装
2.1.1 项目安装
git clone https://github.com/xinntao/Real-ESRGAN.git
cd Real-ESRGAN
2.1.2 安装依赖
# 安装 basicsr - https://github.com/xinntao/BasicSR
# 我们使用BasicSR来训练以及推断
pip install basicsr
# facexlib和gfpgan是用来增强人脸的
pip install facexlib
pip install gfpgan
pip install -r requirements.txt
python setup.py develop

2.2 模型介绍

        模型下载链接,里面有7个,有些我不知道是干啥用的,所以就没说。

  • realesrgan-x4plus(默认)
  • reaesrnet-x4plus
  • realesrgan-x4plus-anime(针对动漫插画图像优化,有更小的体积)
  • realesr-animevideov3 (针对动漫视频)

2.3 代码使用

        将下载好的模型,放在项目文件中的weights文件夹中,然后打开inference_realesrgan.py和inference_realesrgan_video.py这两个文件就运行就行了,一个是图片超分,一个是视频超分。我这里将代码已经全部注释了,自己可以看看很好理解。

        默认模型是realesrgan-x4plus,需要超分的图片/视频放在项目文件夹的inputs中,输出在results中。

import argparse
import cv2
import glob
import os
from basicsr.archs.rrdbnet_arch import RRDBNet
from basicsr.utils.download_util import load_file_from_urlfrom realesrgan import RealESRGANer
from realesrgan.archs.srvgg_arch import SRVGGNetCompactdef main():"""Inference demo for Real-ESRGAN."""parser = argparse.ArgumentParser()  # 创建一个命令行解析器对象,用于解析命令行参数parser.add_argument('-i', '--input', type=str, default='inputs', help='Input image or folder')# 添加一个命令行参数 -i, --input,类型为字符串,默认值为 'inputs',用于指定输入图像或文件夹parser.add_argument('-n','--model_name',type=str,default='RealESRGAN_x4plus',help=('Model names: RealESRGAN_x4plus | RealESRNet_x4plus | RealESRGAN_x4plus_anime_6B | RealESRGAN_x2plus | ''realesr-animevideov3 | realesr-general-x4v3'))# 添加一个命令行参数 -n, --model_name,类型为字符串,默认值为 'RealESRGAN_x4plus',用于指定使用的模型名称parser.add_argument('-o', '--output', type=str, default='results', help='Output folder')# 添加一个命令行参数 -o, --output,类型为字符串,默认值为 'results',用于指定输出文件夹parser.add_argument('-dn','--denoise_strength',type=float,default=0.5,help=('Denoise strength. 0 for weak denoise (keep noise), 1 for strong denoise ability. ''Only used for the realesr-general-x4v3 model'))# 添加一个命令行参数 -dn, --denoise_strength,类型为浮点数,默认值为 0.5,用于指定去噪强度parser.add_argument('-s', '--outscale', type=float, default=4, help='The final upsampling scale of the image')# 添加一个命令行参数 -s, --outscale,类型为浮点数,默认值为 4,用于指定最终的放大倍数parser.add_argument('--model_path', type=str, default=None, help='[Option] Model path. Usually, you do not need to specify it')# 添加一个命令行参数 --model_path,类型为字符串,默认值为 None,用于指定模型路径。通常不需要指定。parser.add_argument('--suffix', type=str, default='out', help='Suffix of the restored image')# 添加一个命令行参数 --suffix,类型为字符串,默认值为 'out',用于指定输出图像的后缀parser.add_argument('-t', '--tile', type=int, default=0, help='Tile size, 0 for no tile during testing')# 添加一个命令行参数 -t, --tile,类型为整数,默认值为 0,用于指定瓦片大小。0 表示测试时没有瓦片。parser.add_argument('--tile_pad', type=int, default=10, help='Tile padding')# 添加一个命令行参数 --tile_pad,类型为整数,默认值为 10,用于指定瓦片填充大小parser.add_argument('--pre_pad', type=int, default=0, help='Pre padding size at each border')# 添加一个命令行参数 --pre_pad,类型为整数,默认值为 0,用于指定每个边界的预填充大小parser.add_argument('--face_enhance', action='store_true', help='Use GFPGAN to enhance face')# 添加一个命令行参数 --face_enhance,动作是存储为 True,用于指定是否使用 GFPGAN 来增强人脸parser.add_argument('--fp32', action='store_true', help='Use fp32 precision during inference. Default: fp16 (half precision).')# 添加一个命令行参数 --fp32,动作是存储为 True,用于指定推理期间是否使用 fp32 精度。默认情况下使用 fp16(半精度)parser.add_argument('--alpha_upsampler',type=str,default='realesrgan',help='The upsampler for the alpha channels. Options: realesrgan | bicubic')# 添加一个命令行参数 --alpha_upsampler,类型为字符串,默认值为 'realesrgan',用于指定 alpha 通道的上采样器。选项:realesrgan | bicubicparser.add_argument('--ext',type=str,default='auto',help='Image extension. Options: auto | jpg | png, auto means using the same extension as inputs')# 添加一个参数,参数名为'--ext',类型为字符串,默认值为auto,这个参数主要用于指定输入图像的扩展名。parser.add_argument('-g', '--gpu-id', type=int, default=None, help='gpu device to use (default=None) can be 0,1,2 for multi-gpu')# 添加一个参数,参数名为'-g'或'--gpu-id',类型为整数,默认值为None。这个参数主要用于指定使用的GPU设备。args = parser.parse_args()# 解析命令行参数,生成一个命名空间args# determine models according to model namesargs.model_name = args.model_name.split('.')[0]# 根据传入的命令行参数--model-name来选择模型,这里假设模型名称和使用的模型之间的关系已经预设好。if args.model_name == 'RealESRGAN_x4plus':  # x4 RRDBNet modelmodel = RRDBNet(num_in_ch=3, num_out_ch=3, num_feat=64, num_block=23, num_grow_ch=32, scale=4)netscale = 4file_url = ['https://github.com/xinntao/Real-ESRGAN/releases/download/v0.1.0/RealESRGAN_x4plus.pth']elif args.model_name == 'RealESRNet_x4plus':  # x4 RRDBNet modelmodel = RRDBNet(num_in_ch=3, num_out_ch=3, num_feat=64, num_block=23, num_grow_ch=32, scale=4)netscale = 4file_url = ['https://github.com/xinntao/Real-ESRGAN/releases/download/v0.1.1/RealESRNet_x4plus.pth']elif args.model_name == 'RealESRGAN_x4plus_anime_6B':  # x4 RRDBNet model with 6 blocksmodel = RRDBNet(num_in_ch=3, num_out_ch=3, num_feat=64, num_block=6, num_grow_ch=32, scale=4)netscale = 4file_url = ['https://github.com/xinntao/Real-ESRGAN/releases/download/v0.2.2.4/RealESRGAN_x4plus_anime_6B.pth']elif args.model_name == 'RealESRGAN_x2plus':  # x2 RRDBNet modelmodel = RRDBNet(num_in_ch=3, num_out_ch=3, num_feat=64, num_block=23, num_grow_ch=32, scale=2)netscale = 2file_url = ['https://github.com/xinntao/Real-ESRGAN/releases/download/v0.2.1/RealESRGAN_x2plus.pth']elif args.model_name == 'realesr-animevideov3':  # x4 VGG-style model (XS size)model = SRVGGNetCompact(num_in_ch=3, num_out_ch=3, num_feat=64, num_conv=16, upscale=4, act_type='prelu')netscale = 4file_url = ['https://github.com/xinntao/Real-ESRGAN/releases/download/v0.2.5.0/realesr-animevideov3.pth']elif args.model_name == 'realesr-general-x4v3':  # x4 VGG-style model (S size)model = SRVGGNetCompact(num_in_ch=3, num_out_ch=3, num_feat=64, num_conv=32, upscale=4, act_type='prelu')netscale = 4file_url = ['https://github.com/xinntao/Real-ESRGAN/releases/download/v0.2.5.0/realesr-general-wdn-x4v3.pth','https://github.com/xinntao/Real-ESRGAN/releases/download/v0.2.5.0/realesr-general-x4v3.pth']# determine model pathsif args.model_path is not None:# 判断是否传入了模型路径,如果传入了则直接使用该路径,否则会结合模型名称生成一个默认的模型路径model_path = args.model_pathelse:model_path = os.path.join('weights', args.model_name + '.pth')if not os.path.isfile(model_path):ROOT_DIR = os.path.dirname(os.path.abspath(__file__))for url in file_url:# model_path will be updatedmodel_path = load_file_from_url(url=url, model_dir=os.path.join(ROOT_DIR, 'weights'), progress=True, file_name=None)# use dni to control the denoise strengthdni_weight = None# dni_weight 为 None 表示不使用 DNI# 如果使用了 DNI,dni_weight 的值会是一个列表,列表的两个元素分别代表 DNI 网络和原始模型的权重if args.model_name == 'realesr-general-x4v3' and args.denoise_strength != 1:wdn_model_path = model_path.replace('realesr-general-x4v3', 'realesr-general-wdn-x4v3')model_path = [model_path, wdn_model_path]dni_weight = [args.denoise_strength, 1 - args.denoise_strength]# restorerupsampler = RealESRGANer(scale=netscale,  # 放大倍率,即超分辨率的因子model_path=model_path,   # 预训练模型的路径dni_weight=dni_weight,  # DNI网络的权重,用于控制去噪强度(Denoising Network Integration)model=model,  # 输入模型,一般是降噪后的图像tile=args.tile,  # 分块大小,即将图像切割成多个小块进行超分辨率tile_pad=args.tile_pad,   # 块与块之间的填充大小pre_pad=args.pre_pad,   # 预处理时的填充大小half=not args.fp32,   # 是否使用半精度浮点数进行计算,若args.fp32为True则使用半精度,否则使用全精度gpu_id=args.gpu_id)  # GPU的ID,用于在多GPU环境下指定使用哪个GPU进行计算if args.face_enhance:  # Use GFPGAN for face enhancement,如果需要使用 GFPGAN 进行人脸增强from gfpgan import GFPGANer  # 导入 GFPGAN 人脸增强器的类face_enhancer = GFPGANer(model_path='https://github.com/TencentARC/GFPGAN/releases/download/v1.3.0/GFPGANv1.3.pth',upscale=args.outscale,  # 放大倍率,即超分辨率的因子arch='clean',   # GFPGAN的架构,这里选择的是'clean'版本channel_multiplier=2,  # 通道的乘数,用于扩大模型的通道数bg_upsampler=upsampler)  # 使用之前创建的RealESRGAN超分辨率增强器作为背景超分辨率增强器# args.output = r"G:\Anaconda\ProjectYOLO\yolov5-7.0\Real-ESRGAN-master\1/"os.makedirs(args.output, exist_ok=True)  # 创建输出目录,如果已存在则不报错,继续执行后续代码if os.path.isfile(args.input):# 判断输入路径是否为一个文件paths = [args.input]# 如果是文件,直接将其路径加入到paths列表中else:paths = sorted(glob.glob(os.path.join(args.input, '*')))# 如果输入路径不是一个文件,那么它应该是一个包含图像的文件夹# 使用glob库获取输入路径下所有的文件路径,并将它们按字母顺序排序后加入到paths列表中for idx, path in enumerate(paths):# 遍历所有的文件路径imgname, extension = os.path.splitext(os.path.basename(path))  # 获取文件名和扩展名print('Testing', idx, imgname)  # 打印正在处理的文件信息img = cv2.imread(path, cv2.IMREAD_UNCHANGED)# 使用OpenCV读取图片,参数cv2.IMREAD_UNCHANGED表示以最接近原始图像的颜色空间读取图像if len(img.shape) == 3 and img.shape[2] == 4:# 判断图像的维度,如果维度为3且第三个维度的大小为4,说明图像是RGBA格式的,否则不进行特殊处理img_mode = 'RGBA'  # 记录图片模式为RGBAelse:img_mode = None  # 否则不记录图片模式try:if args.face_enhance:# 如果需要人脸增强,使用face_enhancer进行人脸增强处理,参数包括输入图像、是否进行人脸对齐、是否只处理中心的人脸部分以及是否将处理后的人脸粘贴回原图_, _, output = face_enhancer.enhance(img, has_aligned=False, only_center_face=False, paste_back=True)else:# 否则,使用upsampler进行图像超分辨率增强,参数包括输入图像、放大倍数以及是否使用GPU加速output, _ = upsampler.enhance(img, outscale=args.outscale)except RuntimeError as error:# 如果在处理过程中出现RuntimeError异常,打印错误信息,并给出可能的解决方案print('Error', error)print('If you encounter CUDA out of memory, try to set --tile with a smaller number.')else:# 如果没有出现异常,执行else分支的代码# 如果用户没有指定输出文件的扩展名,则自动从输入文件的扩展名中获取输出文件的扩展名;否则使用用户指定的扩展名if args.ext == 'auto':extension = extension[1:]else:extension = args.extif img_mode == 'RGBA':  # RGBA images should be saved in png format# 如果图片的模式是RGBA,说明图片是RGBA格式的,需要将其保存为png格式的图片extension = 'png'if args.suffix == '':# 根据用户指定的后缀名构造保存路径save_path = os.path.join(args.output, f'{imgname}.{extension}')else:save_path = os.path.join(args.output, f'{imgname}_{args.suffix}.{extension}')# 使用OpenCV将处理后的图片保存到指定路径下,参数指定保存的文件格式和压缩质量等选项(这里没有指定压缩质量)cv2.imwrite(save_path, output)# 保存处理后的图片到指定路径下if __name__ == '__main__':main()

2.4 命令行使用

2.4.1 参数
Usage: python inference_realesrgan.py -n RealESRGAN_x4plus -i infile -o outfile [options]...A common command: python inference_realesrgan.py -n RealESRGAN_x4plus -i infile --outscale 3.5 --face_enhance-h                   show this help-i --input           Input image or folder. Default: inputs-o --output          Output folder. Default: results-n --model_name      Model name. Default: RealESRGAN_x4plus-s, --outscale       The final upsampling scale of the image. Default: 4--suffix             Suffix of the restored image. Default: out-t, --tile           Tile size, 0 for no tile during testing. Default: 0--face_enhance       Whether to use GFPGAN to enhance face. Default: False--fp32               Whether to use half precision during inference. Default: False--ext                Image extension. Options: auto | jpg | png, auto means using the same extension as inputs. Default: auto
2.4.2 参数使用
python inference_realesrgan.py -n RealESRGAN_x4plus_anime_6B -i inputs

3 桌面端轻应用

        作者提供了打包好的桌面端exe程序,无需配置PyTorch等依赖,Windows下载地址。

        使用方法也很简单,图片放在realesrgan-ncnn-vulkan.exe同目录下,然后使用cmd命令行跳转至这个目录,输入下面的命令(自己修改)。

./realesrgan-ncnn-vulkan.exe -i 输入图像.jpg -o 输出图像.png -n 模型名字

        注意:可执行文件并没有支持 python 脚本 inference_realesrgan.py 中所有的功能,比如 outscale 选项) .

Usage: realesrgan-ncnn-vulkan.exe -i infile -o outfile [options]...-h                   show this help-i input-path        input image path (jpg/png/webp) or directory-o output-path       output image path (jpg/png/webp) or directory-s scale             upscale ratio (can be 2, 3, 4. default=4)-t tile-size         tile size (>=32/0=auto, default=0) can be 0,0,0 for multi-gpu-m model-path        folder path to the pre-trained models. default=models-n model-name        model name (default=realesr-animevideov3, can be realesr-animevideov3 | realesrgan-x4plus | realesrgan-x4plus-anime | realesrnet-x4plus)-g gpu-id            gpu device to use (default=auto) can be 0,1,2 for multi-gpu-j load:proc:save    thread count for load/proc/save (default=1:2:2) can be 1:2,2,2:2 for multi-gpu-x                   enable tta mode"-f format            output image format (jpg/png/webp, default=ext/png)-v                   verbose output

        由于这些exe文件会把图像分成几个板块,然后来分别进行处理,再合成导出,输出的图像可能会有一点割裂感(而且可能跟PyTorch的输出不太一样)。

4 总结

        这个开源项目总体来说精度是不错的,图像的分辨率确实有明显的提升,可以将模糊的图片还原出更多的细节,但有时候的效果比较抽象。作者在项目中说会持续更新(PS:作者的重心好像是放在动漫图片超分方面),希望会越来越好。最后分享一下腾讯ARC的Web端使用demo。

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

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

相关文章

CSS 文字溢出省略号显示

1. 单行文本溢出显示省略号 需要满足三个条件,添加对应的代码: (1)先强制一行内显示文本; (2)超出的部分隐藏; (3)文字用省略号来替代省略的部分&#xf…

IDEA 使用Reset Current Branch to Here 进行git 版本控制,图文操作

文章目录 一、总结区别(只针对本地仓库操作)Soft详细解释文件版本冲突处理 Mixed详细解释Hard详细解释Keep详细解释文件版本冲突处理 二、其他Revert commit 参考文档 一、总结区别(只针对本地仓库操作) Soft详细解释 Soft操作只…

docker命令大全

1、查看Docker 容器占用的空间 docker ps -s2、查看所有容器 docker ps -a3、启动、关闭、重启一个已存在的容器 docker start <容器ID> docker stop <容器ID> docker restart <容器ID> 4、进入容器&#xff0c;退出终端的时候不会关闭container的ma…

龙讯旷腾PWmat:新的催化反应机理——瞬态相变,对多相电催化剂的设计和多相电催化机理的研究具有重要意义

研究背景 众所周知&#xff0c;材料的性质&#xff0c;包括催化活性都是相敏感的。而材料的相与外界条件有关&#xff0c;电催化反应过程中的外部条件与反应前后的外部条件不同&#xff0c;这自然导致了一个问题&#xff1a;在反应过程中电催化剂的相是否可以与反应前后的相不…

C 语言数组

C 语言数组 在本教程中&#xff0c;您将学习如何使用数组。您将借助示例学习如何声明&#xff0c;初始化和访问数组的元素。 数组是可以存储多个值的变量。例如&#xff0c;如果要存储100个整数&#xff0c;则可以为其创建一个数组。 示例 cint data[100];如何声明数组&…

线程池的使用

线程池的作用 降低线程创建和销毁的开销&#xff1a;线程的创建和销毁是比较昂贵的操作。通过使用线程池&#xff0c;可以避免频繁地创建和销毁线程&#xff0c;而是复用线程池中已经存在的线程&#xff0c;从而降低了开销。 控制并发度&#xff1a;通过控制线程池中线程的数量…

MySQL(14):视图

数据库对象 对象描述表(TABLE)表是存储数据的逻辑单元&#xff0c;以行和列的形式存在&#xff0c;列就是字段&#xff0c;行就是记录数据字典就是系统表&#xff0c;存放数据库相关信息的表。系统表的数据通常由数据库系统维护&#xff0c;程序员通常不应该修改&#xff0c;只…

mysql 讲解(1)

文章目录 前言一、基本的命令行操作二、操作数据库语句2.1、创建数据库2.2、删除数据库2.3、使用数据库2.4 查看所有数据库 三、列的数据类型3.1 字符串3.2 数值3.3 时间日期3.4 空3.5 int 和 varchar问题总结&#xff1a; 四、字段属性4.1 UnSigned4.2 ZEROFILL4.3 Auto_InCre…

ARPG----C++学习记录05 Section12 动画蒙太奇,收拿剑,MetaSound,调整动画

代码更新 https://github.com/BAOfanTing/ARPG_Game_Code/commit/c629270e49496ba1bcbaf03780d23c1842ca5e7a Animation Montages动画蒙太奇 蒙太奇的工作流程 新建一个鼠标左键的按键映射&#xff0c;下载一些攻击动画&#xff0c;重定向给我们的人物&#xff0c;新建一个动画…

若依系统富文本框上传图片报错!

报错如下&#xff1a; 原因&#xff1a;如图&#xff0c;富文本路径中存在 / 字符&#xff0c;导致上传出错。 解决方案&#xff1a;将富文本框内容在前端进行加密&#xff0c;后端再解密。 前端&#xff1a; 安装 crypto-js 插件 npm install crypto-js 创建工具类 :在 sr…

使用MVS-GaN HEMT紧凑模型促进基于GaN的射频和高电压电路设计

标题&#xff1a;Facilitation of GaN-Based RF- and HV-Circuit Designs Using MVS-GaN HEMT Compact Model 来源&#xff1a;IEEE TRANSACTIONS ON ELECTRON DEVICES&#xff08;19年&#xff09; 摘要—本文阐述了基于物理的紧凑器件模型在研究器件行为细微差异对电路和系统…

好心提醒下,幼师姐妹们要知道啊

幼师家人们在不在&#xff1f;在不在&#xff1f; 不会还有姐妹在自己写教案&#xff0c;写总结&#xff0c;写评语啥的吧&#xff0c;这个好东西真的要知道啊&#xff01;&#xff01; 只要输入关键词&#xff0c;马上就能得到你想要的内容&#xff0c;真的很强啊&#xff0…

Pytorch从零开始实战09

Pytorch从零开始实战——YOLOv5-Backbone模块实现 本系列来源于365天深度学习训练营 原作者K同学 文章目录 Pytorch从零开始实战——YOLOv5-Backbone模块实现环境准备数据集模型选择开始训练可视化模型预测总结 环境准备 本文基于Jupyter notebook&#xff0c;使用Python3.…

【java学习—十四】Class类(2)

文章目录 1. Class类2. Class类的常用方法3. 实例化Class类对象&#xff08;四种方法&#xff09; 1. Class类 在 Object 类中定义了以下的方法&#xff0c;此方法将被所有子类继承&#xff1a; public final Class getClass() 以上的方法返回值的类型是一个 Class 类&#xf…

web3 React dapp进行事件订阅

好啊&#xff0c;上文web3 React Dapp书写订单 买入/取消操作 我们已经写好了 填充和取消订单 这就已经是非常大的突破了 但是 留下了一个问题 那就是 我们执行完之后 订单的数据没有直接更新 每次都需要我们手动刷新 才能看到结果 那么 今天我们就来看解决这个问题的事件订阅 …

android手机平板拓展电脑音频

&#xff08;1&#xff09;首先确保电脑上有声卡&#xff0c;就是电脑右下角小喇叭能调音量&#xff0c;不管电脑会不会响&#xff0c;如果小喇叭标记了个错误&#xff0c;说明没有声卡&#xff0c;安装图上的虚拟声卡软件。 &#xff08;2&#xff09;图上第一个PC免安装及局…

vscode launch.json

有时新的服务器进行调试时&#xff0c;需要设置调试的launch.json的结果 然后就可以打开一个launch.json 其内容如下 {// 使用 IntelliSense 了解相关属性。 // 悬停以查看现有属性的描述。// 欲了解更多信息&#xff0c;请访问: https://go.microsoft.com/fwlink/?linkid83…

JAVA 版小程序商城免费搭建 多商家入驻 直播带货 商城系统 B2B2C 商城源码之 B2B2C产品概述

1. 涉及平台 平台管理、商家端&#xff08;PC端、手机端&#xff09;、买家平台&#xff08;H5/公众号、小程序、APP端&#xff08;IOS/Android&#xff09;、微服务平台&#xff08;业务服务&#xff09; 2. 核心架构 Spring Cloud、Spring Boot、Mybatis、Redis 3. 前端框架…

[单片机课程设计报告汇总] 单片机设计报告常用硬件元器件描述

[单片机课程设计必看] 单片机设计报告常用描述 硬件设计 AT89C51最小系统 AT89C51是美国ATMEL公司生产的低电压&#xff0c;高性能CMOS16位单片机&#xff0c;片内含4k bytes的可反复擦写的只读程序存储器和128 bytes的随机存取数据存储器&#xff0c;期间采用ATMEL公司的高…

数据结构—队列的实现

前言&#xff1a;上次我们已经学习了数据结构中一个重要的线性表—栈&#xff0c;那么我们这一次就来学习另外一个重要的线性表—队列。 目录&#xff1a; 一、 队列的概念 二、 队列的实现&#xff1a; 1.队列的创建 三、 队列的操作 1.初始化队列 2.队尾入队列 3.队头出队列…