[Redis] Redis数据持久化

🌸个人主页:https://blog.csdn.net/2301_80050796?spm=1000.2115.3001.5343
🏵️热门专栏:
🧊 Java基本语法(97平均质量分)https://blog.csdn.net/2301_80050796/category_12615970.html?spm=1001.2014.3001.5482
🍕 Collection与数据结构 (92平均质量分)https://blog.csdn.net/2301_80050796/category_12621348.html?spm=1001.2014.3001.5482
🧀线程与网络(96平均质量分) https://blog.csdn.net/2301_80050796/category_12643370.html?spm=1001.2014.3001.5482
🍭MySql数据库(93平均质量分)https://blog.csdn.net/2301_80050796/category_12629890.html?spm=1001.2014.3001.5482
🍬算法(97平均质量分)https://blog.csdn.net/2301_80050796/category_12676091.html?spm=1001.2014.3001.5482
🍃 Spring(97平均质量分)https://blog.csdn.net/2301_80050796/category_12724152.html?spm=1001.2014.3001.5482
🎃Redis(97平均质量分)https://blog.csdn.net/2301_80050796/category_12777129.html?spm=1001.2014.3001.5482
🐰RabbitMQ(97平均质量分) https://blog.csdn.net/2301_80050796/category_12792900.html?spm=1001.2014.3001.5482
感谢点赞与关注~~~
在这里插入图片描述

目录

  • 1. 持久化概述
  • 2. 持久化的策略
    • 2.1 RDB模式
      • 2.1.1 持久化策略
      • 2.1.2 触发机制
    • 2.2 AOF模式
      • 2.2.1 持久化策略
      • 2.2.2 重写机制
      • 2.2.3 触发条件
  • 3. 混合持久化

1. 持久化概述

我们之前在学习MySQL数据库的时候,我们学习过MySQL事务的四个比较核心的特性:分别是原子性(把对多个表的操作打包为一个操作),一致性(事务前后的数据都是合法数据,比如同一个操作中同时减少和增加一个值,要不同时成功,要不同时失败,不能出现中间状态),持久性(把数据存储在硬盘上),隔离性(脏读,不可重复读,幻读,串行化).
我们知道,我们学习的redis,是把数据存在内存中的,但是我们知道,数据存储在内存中的数据是不持久的,但是redis为了持久化,数据还是要想办法保存在硬盘上的.其中硬盘上的数据只是在redis重启的时候,用来恢复数据使用的.
当我们要插入一个数据的时候,就需要把这个数据同时写入到内存和硬盘中.但是在写硬盘的时候,具有不同的策略.

2. 持久化的策略

Redis在实现持久化的时候,具体是按照以下两种方式来实现的,一种是RDB(Redis Database)模式,一种是AOF(Append Only File)模式.其中的RDB采用的备份模式是定期备份,也就是每隔一段时间,就会把内存中的数据备份到硬盘中.而AOF使用的是实时备份,只要内存中出现了新的数据,就会立即备份到硬盘中.

2.1 RDB模式

2.1.1 持久化策略

RDB在硬盘中备份数据的时候,采用的是生成"快照"的方式.

何为生成快照,就像警察来到案发现场一样,对没有破坏的案发现场进行拍照,按照照片上提供的线索对现场当时的情况进行还原.

Redis生成快照的方式也是类似的,Redis在内存中存储数据之后,Redis会给这些数据进行"拍照",生成一个文件,存储在硬盘中.后续在Redis重启之后,就可以根据刚才生成的快照,把内存中的数据进行恢复处理.

2.1.2 触发机制

我们知道,RDB模式的持久化是定期触发的.关于"定期",具体来说,有两种方式.

  1. 手动触发
    程序员可以通过Redis客户端来执行特定的命令来触发快照的生成.这个命令一共有两种,一种是save命令,一种是bgsave命令.其中save命令执行的时候,Redis就会全力以赴的进行"快照生成"操作,此时就会阻塞Redis的其他客户端的命令,结果类似与keys *,所以我们一般不建议使用save命令.
    之后是bgsave命令,这个命令就不会影响到Redis服务器处理其他客户端的请求和命令.之所以不会影响到其他的Redis客户端,是由于Redis引入了多进程的方式来实现这个功能.其中一个进程负责继续接收客户端的请求,另一个进程负责生成快照并存储到硬盘中.也就是Redis会创建出一个子进程,子进程会完成持久化操作.持久化会把数据写入到新的文件中,然后使用新的文件替换旧的文件.关于文件是否被替换,我们可以使用Linux的stat命令来查看文件的iNode编号.在执行bgsave命令之后,我们发现文件的iNode有变化.下面是bgsave的执行流程:
    在这里插入图片描述
    下面我们来查看执行bgsave前后两次的iNode.
    在这里插入图片描述
    执行bgsave之后:
    在这里插入图片描述

我们需要注意的一点就是,save命令是直接在之前的旧文件上写入数据,所以在执行save命令之后,dump.rdb文件的iNode不会改变.

下面我们来对bgsave的实际效果进行展示:

127.0.0.1:6379> FLUSHALL
OK
127.0.0.1:6379> set key1 value1
OK
127.0.0.1:6379> bgsave
Background saving started
root@iZ2ze9pwr3i8b65w9dr55dZ:~# service redis-server restart
root@iZ2ze9pwr3i8b65w9dr55dZ:~# redis-cli
127.0.0.1:6379> keys *
1) "key1"

我们发现,在bgsave之后,在我们重新启动服务器的时候,其中的key1没有丢失.
但是快照生成也不是手动输入bgsave命令或者save命令的时候才会触发快照生成,当执行一下操作的时候,也会自动触发触发快照生成:
- 重新启动Redis服务器的时候.
- 下面要讲述的自动生成配置符合相应条件的时候.
- Redis进行主从复制的时候,主结点会自动生成RDB快照,然后把RDB快照通过网络发送给从结点.
比如我们下面不执行快照生成相关命令,直接重新启动Redis服务器.

root@iZ2ze9pwr3i8b65w9dr55dZ:~# redis-cli
127.0.0.1:6379> keys *
1) "key1"
127.0.0.1:6379> set key2 value2
OK
127.0.0.1:6379> 
root@iZ2ze9pwr3i8b65w9dr55dZ:~# service redis-server restart
root@iZ2ze9pwr3i8b65w9dr55dZ:~# redis-cli
127.0.0.1:6379> keys *
1) "key2"
2) "key1"

我们发现Redis中的数据仍然存在.
如果我们直接使用kill -9命令直接终止Redis相关进程,Redis就会来不及生成快照,导致数据直接丢失.

root@iZ2ze9pwr3i8b65w9dr55dZ:~# redis-cli
127.0.0.1:6379> set key3 value3
OK
127.0.0.1:6379> 
root@iZ2ze9pwr3i8b65w9dr55dZ:~# ps -aux|grep redis
redis     370001  0.1  0.8  67864 14080 ?        Ssl  21:24   0:00 /usr/bin/redis-server 0.0.0.0:6379
root      370248  0.0  0.1   6544  2304 pts/0    S+   21:30   0:00 grep --color=auto redis
root@iZ2ze9pwr3i8b65w9dr55dZ:~# kill -9 370001
root@iZ2ze9pwr3i8b65w9dr55dZ:~# ps -aux|grep redis
redis     370253  0.5  0.8  67864 13824 ?        Ssl  21:30   0:00 /usr/bin/redis-server 0.0.0.0:6379
root      370294  0.0  0.1   6544  2304 pts/0    S+   21:31   0:00 grep --color=auto redis
root@iZ2ze9pwr3i8b65w9dr55dZ:~# redis-cli
127.0.0.1:6379> keys *
1) "key1"
2) "key2"

我们看到key3数据直接丢失了.

  1. 自动触发

自动触发的其他情况我们在上面讲述过,下面我们只讲述通过配置文件进行定期快照生成.

RDB快照的生成是定期生成,所以我们可以在Redis的配置文件中设置让Redis每隔多长时间就触发一次.其中的配置项是save配置项.
在这里插入图片描述
这些配置项指的是:如果在900秒之内只有1个键值对的修改,那么就是没900秒触发一次.以此类推.当我们把save配置项设置为一个空字符串(“”)的时候,这时候就会关闭快照的定期自动生成.

虽然这些值都可以随便修改,但是我们有一个基本的原则,就是生成一次RDB快照是一个成本比较高的操作,不能让这个操作执行太频繁.
正是由于RDB的快照生成不可以太频繁,这就导致了快照里的数据和当前的实时数据情况可能出现一定的偏差.

比如12点的时候生成了RDB文件,12点01秒开始的时候,redis开始收到了大量的key变化的请求,按照默认配置,RDB至少在12点01分的时候才会生成下一个RDB镜像文件,但是在这期间,Redis服务崩溃,这就导致了12点之后的这些数据全部丢失.

redis生成的RDB文件存放在Redis的工作目录中(默认/var/lib/redis,可以在配置文件中修改).其中有一个dump.rdb文件.这个是Redis的RDB机制生成的镜像文件,Redis服务器就是默认开启了RDB的.这个文件就是RDB保存在硬盘中的持久化文件.
在这里插入图片描述
这个文件是一个二进制文件,这个文件就是把内存中的数据以压缩的形式保存到这个二进制文件中的.(使用这种压缩的形式保存,虽然会消耗一定的CPU资源,但是可以节省一定的硬盘空间).
在这里插入图片描述
这个文件一般不可以轻易修改,改坏就麻烦了.如果这个文件被改坏了,后续在Redis服务重新启动的时候,Redis会尝试加载这个RDB格式的文件.如果发现这个RDB文件格式错误,或者意外损坏.Redis服务就会启动失败.当然某些情况下还是可以启动成功的,但是这时候Redis中的数据就不是我们期望的数据,就和"开盲盒"一样.
所以Redis提供了RDB文件检查工具,redis-check-rdb <rdb文件路径> 命令可以对rdb是否损坏进行检查.
在这里插入图片描述
RDB文件的路径可以在配置文件中做出修改.具体是dir配置项.文件名也可以在配置文件中做出修改,具体的配置项是dbfilename.
在这里插入图片描述
在这里插入图片描述

2.2 AOF模式

上述的RDB机制,有一定优点,也有一定的缺点.

  • RDB是⼀个紧凑压缩的⼆进制文件,代表Redis在某个时间点上的数据快照。非常适用于备份,全量复制等场景。比如每6小时执行bgsave备份,并把RDB文件复制到远程机器或者文件系统中(如hdfs)用于灾备.
  • Redis加载 RDB恢复数据远远快于AOF的方式,因为RDB是以二进制的格式保存数据的,恢复的时候直接读取的就是二进制的数据,也就是直接按照字节的方式读取出来的.我们知道Redis存储数据的方式就是直接存储的是二进制数据,没有进行过编码.
  • RDB方式数据没办法做到实时持久化/秒级持久化。因为bgsave每次运行都要执行fork创建子进程,属于重量级操作,频繁执行成本过高
  • RDB文件使用特定⼆进制格式保存,Redis版本演进过程中有多个RDB版本,兼容性可能有风险
  • RDB最大的缺点还是保存数据的时候是定期保存的,不是实时保存的,这就可能导致生成快照之间,实时的数据可能会随着Redis服务的意外终止而丢失.

为了解决上面RDB的一些缺点,我们引入了AOF机制.

2.2.1 持久化策略

AOF的持久化策略有点类似与MySQL的binlog,把用户的每个操作都记录到文件中,当Redis重新启动的时候,就会读取这个AOF文件内容,用来恢复数据.
其中AOF文件是一个文本文件,每次进行的操作都会被记录到这个文本文件中,通过一些特殊符号作为分隔符,来对命令的细节做出区分.

AOF一般默认是关闭状态,我们需要通过修改配置文件来开启AOF功能.重启Redis服务之后生效.
在这里插入图片描述
其中appendfilename配置用来修改AOF的文件名.
在这里插入图片描述
AOF持久化文件的默认路径和RDB持久化文件一样,都是/var/lib/redis目录下.
在这里插入图片描述
AOF机制在备份数据的时候,不是直接让工作线程写入硬盘,而是先写入一个内存中的缓存区,积累一波之后,再统一写入硬盘.这就使得写硬盘的次数大大减少.
在这里插入图片描述
其次,AOF每次把新的操作写入到原有文件的末尾,属于顺序写入.而顺序写入的速度是比较快的.正是由于上面的两点,使得AOF虽然既要写内存又要写硬盘,但是他的效率没有降低多少.
但是如果把数据写在缓冲区的时候,本质上还是写在缓存中的,如果注解突然掉电或者进程崩溃,缓冲区的数据就会丢失.这时候,Redis就给出了一些同步硬盘中AOF文件的频率选项,也就是更新缓冲区数据的频率选项.
在这里插入图片描述
刷新频率越高,性能影响越大,同时数据的可靠性越高,刷新频率越低,性能影响越小,数据的可靠性越低.
缓冲区刷新率也可以在配置文件中进行配置.具体的配置项是appendfsync,程序员可以根据自己的需要进行更改.
在这里插入图片描述

2.2.2 重写机制

  • 概述
    随着AOF文件体积的持续增长,体积会越来越大,这就会影响到Redis的下次启动的启动时间.Redis在启动的时候,需要读取AOF文件的内容,我们知道,在AOF中记录的是我们操作Redis的中间过程.实际上,Redis在重新启动的时候,关注的是最终的结果.这时候,AOF就可以把一些冗余的数据进行优化,剔除其中的冗余操作,并且合并一些操作,达到给AOF瘦身的效果,这就是AOF的重写机制.

比如我们有如下的操作:
lpush key 111
lpush key 222
这时候Redis就会合并这些操作,合并为lpush key 111 222.
再比如:
set key 111
set key 222
这时候Redis只会在AOF中保存set key 222这一个操作.

  • 流程
    AOF重写的机制首先需要创建一个子进程fork.父进程仍然负责接收请求,子进程负责对AOF文件进行重写.

注意: 重写的时候,不关心AOF文件中原来都有什么,只是关心内存中最终的数据状态.子进程只需要把内存中当前的数据获取出来,以AOF文件的格式写入到一个新的AOF文件中.

下面是AOF的重写机制:

此处的子进程写数据的过程,非常类似与RDB生成快照的过程,只不过RDB这里是按照二进制的方式来生成的,而AOF重写则是按照文本格式来生成的.

在这里插入图片描述子进程写新的AOF文件的同时,父进程仍然还在不停地接收客户端的请求.父进程还是会把这些请求产生的AOF数据写入到缓冲区,之后再写入旧的AOF文件中.

  • 问题:
    • 父进程再fork完毕之后,就已经让子进程写AOF文件了.并且随着时间的推移,子进程很快就会写完新的AOF文件,要让新的AOF文件代替旧的,此时父进程再写这个即将消亡的AOF文件还是否有意义?
      有,我们需要考虑到一些极端的情况,比如重写了一半,子进程或者服务器挂掉了,子进程的内存数据就会丢失,新的AOF就会不完整.所以父进程还是会坚持写旧的AOF文件.

在子进程创建的一瞬间,子进程就继承了父进程当前的内存状态,因此,子进程里的内存数据是父进程fork之前的状态,fork之后新来的请求对内存造成的修改是子进程不知道的.此时,父进程这里又准备了一个aof_rewrite_buf缓冲区,专门存放fork之后收到的数据.子进程在把AOF数据全部写完之后,会通过信号通知父进程,父进程再把aof_rewrite_buf缓冲区的内容也写到新的AOF文件中.此时就可以用新的AOF文件代替旧的AOF文件了.

  • 问题:
    • 如果在执行bgrewirteaof的时候,当前Redis已经在AOF重写,会怎么样?
      此时不会在进行AOF重写了,直接返回.
    • 如果在执行bgrewirteaof的时候,发现当前Redis在生成RDB快照文件,会怎么样?
      此时AOF重写操作就会等待,等待RDB快照生成完成之后,再进行AOF重写.

2.2.3 触发条件

  • 手动触发
    可以调用bgrewriteaof指令来进行触发
  • 自动触发
    可以根据auto-aof-rewrite-min-sizeauto-aof-rewrite-percentage参数确定自动触发时机.
    在这里插入图片描述
    第一个表示的是当前AOF占用大小相比较上次重写时增加的比例.第二个表示的是触发重写的AOF文件的大小.
  • 优先级
    如果Redis上同时存在AOF文件和RDB快照的时候,此时以AOF文件为主,RDB直接被忽略.
    在这里插入图片描述

3. 混合持久化

AOF本来是按照文本的方式来写入文件的.但是以文本的方式来写文件,成本是比较高的,于是Redis就引入了混合持久化.结合了RDB和AOF的特点.具体的配置项是aof-use-rdb-preamble选项.修改配置之后需要重启服务器.

这个配置启动之后,就会按照AOF的妨害,每一个请求/操作都录入文件中,在触发AOF重写之后,就会把当前内存的状态按照RDB的二进制格式写入到新的AOF文件中,后续再进行操作的时候,任然是按照AOF文本的格式追加到文件后面的.

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

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

相关文章

【设计模式系列】装饰器模式

目录 一、什么是装饰器模式 二、装饰器模式中的角色 三、装饰器模式的典型应用场景 四、装饰器模式在BufferedReader中的应用 一、什么是装饰器模式 装饰器模式是一种结构型设计模式&#xff0c;用于在不修改对象自身的基础上&#xff0c;通过创建一个或多个装饰类来给对象…

数据结构与算法分析:你真的理解排序算法吗——计数排序(代码详解)

一、算法描述 一个会计师负责对一个小饭店的账本进行审核。每天晚上饭店打洋时&#xff0c;饭店主人记录白 天的总销售额&#xff0c;然后打印出有总额和日期的收据。这些收据存放在一个大盒子里面.每 年年终&#xff0c;会计师审核盒子中的这些收据&#xff0c;检查是否有的已…

Java.6--多态-设计模式-抽象父类-抽象方法

一、多态 1.定义--什么是多态&#xff1f; a.同一个父类的不同子类对象&#xff0c;在做同一行为的时候&#xff0c;有不同的表现形式&#xff0c;这就是多态。&#xff08;总结为&#xff1a;一个父类下的不同子类&#xff0c;同一行为&#xff0c;不同表现形式。&#xff0…

【力扣】GO解决子序列相关问题

文章目录 一、引言二、动态规划方法论深度提炼子序列问题的通用解法模式 三、通用方法论应用示例&#xff1a;最长递增子序列&#xff08;LeetCode题目300&#xff09;Go 语言代码实现 四、最长连续递增序列&#xff08;LeetCode题目674&#xff09;Go 语言代码实现 五、最长重…

目前最新 Reflector V11.1.0.2067版本 .NET 反编译软件

目前最新 Reflector V11.1.0.2067版本 .NET 反编译软件 一、简介二、.NET Reflector的主要功能包括&#xff1a;1. **反编译**: 反编译是将已编译的.NET程序集&#xff08;如.dll或.exe文件&#xff09;转换回可读的源代码。这使得开发者可以查看和学习第三方库的实现细节&…

手机淘宝自动下单退货自动化RPA脚本机器人

使用手机集线器连接多个手机并发运行。 脚本分3个部分&#xff08;读取本地连接下单&#xff0c;退货获取退货地址信息&#xff0c;填写快递单号&#xff09; 脚本部分图结构看下面的图片 部分数据统计展示

基于vue框架的的高校设备信息管理系统的设计与实现tx6d7(程序+源码+数据库+调试部署+开发环境)系统界面在最后面。

系统程序文件列表 项目功能&#xff1a;设备管理员,设备维护员,设备类别,设备,设备入库,设备分发,设备调拨,定期维护,维护任务,设备运行记录 开题报告内容 基于Vue框架的高校设备信息管理系统的设计与实现开题报告 一、项目背景及意义 随着高校教育事业的蓬勃发展&#xff…

线性代数学习

1.标量由只有一个元素的张量表示 import torchx torch.tensor([3,0]) y torch.tensor([2,0])x y, x * y, x / y, x**y 2.可以将向量视为标量值组成的列表 x torch.arange(4) x 3.通过张量的索引访问任一元素 x[3] 4.访问张量长度 len(x) 5.只有一个轴的张量&#xff0c…

gin入门教程(10):实现jwt认证

使用 github.com/golang-jwt/jwt 实现 JWT&#xff08;JSON Web Token&#xff09;可以有效地进行用户身份验证,这个功能往往在接口前后端分离的应用中经常用到。以下是一个基本的示例&#xff0c;演示如何在 Gin 框架中实现 JWT 认证。 目录结构 /hello-gin │ ├── cmd/ …

Could not retrieve mirrorlist http://mirrorlist.centos.org错误解决方法

文章目录 背景解决方法 背景 今天在一台新服务器上安装nginx&#xff0c;在这个过程中需要安装相关依赖&#xff0c;在使用yum install命令时&#xff0c;发生了以下报错内容&#xff1a; Could not retrieve mirrorlist http://mirrorlist.centos.org/?release7&archx8…

【永中软件-注册/登录安全分析报告】

前言 由于网站注册入口容易被黑客攻击&#xff0c;存在如下安全问题&#xff1a; 暴力破解密码&#xff0c;造成用户信息泄露短信盗刷的安全问题&#xff0c;影响业务及导致用户投诉带来经济损失&#xff0c;尤其是后付费客户&#xff0c;风险巨大&#xff0c;造成亏损无底洞…

第二十九篇:TCP的报文格式,TCP系列三

TCP是协议&#xff0c;是协议就有协议格式。 1.源端口和目的端口 TCP源端口&#xff08;Source Port&#xff09;&#xff1a;源计算机上的应用程序的端口号&#xff0c;占 16 位。 TCP目的端口&#xff08;Destination Port&#xff09;&#xff1a;目标计算机的应用程序端口…

政安晨【零基础玩转各类开源AI项目】基于本地Ubuntu (Linux ) 系统应用Gradio-Lite:无服务器 Gradio 完全在浏览器中运行

目录 简介 什么是@gradio/lite? 入门 1.导入 JS 和 CSS 2. 创建标签 3. 在标签内编写你的 Gradio 应用程序 更多示例:添加其他文件和要求 多个文件 其他要求 SharedWorker 模式 代码和演示playground 1.无服务器部署 2.低延迟 3. 隐私和安全 限制 尝试一下!…

基于Python+SQL Server2008实现(GUI)快递管理系统

快递业务管理系统的设计与实现 摘要: 着网络新零售的到来&#xff0c;传统物流在网购的洗礼下迅速蜕变&#xff0c;在这场以互联网为基础的时代变革中&#xff0c;哪家企业能率先转变其工作模式就能最先分得一杯羹&#xff0c;物流管理也不例外。传统的物流管理模式效率低下&a…

同城分类信息网站源码系统 PHP+MySQL组合开发 带完整的安装代码包以及搭建部署教程

系统概述 该系统采用PHP作为后端开发语言&#xff0c;MySQL作为数据库管理系统。PHP是一种广泛使用的开源脚本语言&#xff0c;特别适合于Web开发&#xff0c;具有跨平台、易于学习、性能稳定等优点。MySQL则是一款轻量级的关系型数据库管理系统&#xff0c;具有体积小、速度快…

DHorse v1.6.0 发布,基于 k8s 的发布平台

版本说明 新增特性 支持Codeup&#xff08;阿里云云效&#xff09;代码仓库&#xff1b;支持环境的自动部署&#xff1b; 优化特性 管理员角色部署环境部需要审批&#xff1b;优化页面展示&#xff1b; 升级指南 升级指南 DHorse介绍 DHorse是一个轻量级、简单易用的云…

微服务网关Zuul

一、Zuul简介 Zuul是Netflix开源的微服务网关&#xff0c;包含对请求的路由和过滤两个主要功能。 1&#xff09;路由功能&#xff1a;负责将外部请求转发到具体的微服务实例上&#xff0c;是实现外部访问统一入口的基础。 2&#xff09;过滤功能&#xff1a;负责对请求的过程…

crc, md5 和 sha的区别

效率不同: 直接看代码 import zlib import hashlib import timewith open(rD:\data., rb) as f:x f.read()s time.time() for i in range(100000):d zlib.crc32(x) print(time.time() - s)s time.time() for i in range(100000):m hashlib.md5()m.update(x)d m.hexdige…

【CSS】纯CSS Loading动画组件

<template><div class"ai-loader-box"><!-- AI loader --><div class"ai-loader"><div class"text"><p>AI智能分析中....</p></div><div class"horizontal"><div class&quo…

idea项目搭建的四种方式: 一(以idea2017为例)

目录 1. 普通java项目 2. 普通JavaWEB项目 3. maven的JavaWEB项目 4. maven的java项目 1. 普通java项目 ①点击“Create New Project”&#xff1b; ②选择“Java”&#xff0c;选择自己安装的jdk&#xff0c;点击“Next”&#xff1b; ③填好项目名称和路径&#xff1b;…