当前位置: 首页 > news >正文

深入解析 EasyExcel 组件原理与应用

深入解析 EasyExcel 组件原理与应用

官方:EasyExcel官方文档 - 基于Java的Excel处理工具 | Easy Excel 官网

在日常的 Java 开发工作中,处理 Excel 文件的导入导出是极为常见的需求。
今天,咱们就一起来深入了解一款非常实用的操作 Excel 的组件 ——EasyExcel,看看它究竟有着怎样的神奇之处,能让众多开发者青睐有加。

一、引言

想必大家都知道,在 Java 领域中,Apache POI 是处理 Excel 文件的老牌工具了。但随着业务发展,面对越来越大的 Excel 文件读写需求时,POI 暴露出了一些诸如内存溢出(OOM)等问题,使用起来稍显吃力。而 EasyExcel 的出现,很好地弥补了这些不足,它基于 POI 进行了优化封装,为我们提供了更加简洁高效的 Excel 处理方式。接下来,咱们就详细剖析一下 EasyExcel 的原理以及它的具体应用。

二、EasyExcel 与 Apache POI 的渊源

EasyExcel 其实是站在 Apache POI 这个 “巨人的肩膀” 上发展起来的。Apache POI 基于 OOXML(Office Open XML)标准(像 xlsx、docx、pptx 等以指定格式的 xml 为基础并以 zip 格式压缩的文件)和 OLE2 标准(包括 xls、doc、ppt 等二进制格式的文件),只要符合上述标准的文件它都能进行读写操作。

对于 xlsx 文件来说,它基于 OOXML 标准,能够解压成对应的 xml 文件,在解析后的 xml 文件里,我们重点关注 sharedStrings.xml 与 sheet1.xml 这两个 xml 节点,因为里面存放着我们想要处理的 Excel 内容。

不过,POI 在处理 Excel 时有传统的 POM 解析和 SAX 解析两种方式。传统的 POM 解析会把 Excel 中的所有 XML 节点解析成一棵 DOM 树,整棵 DOM 树加载进内存,这样做虽然方便对每个 XML 节点进行随机访问,但很容易导致内存溢出现象,像仅仅 3 列的 Excel 文件在 7 万行左右就可能出现内存溢出问题。

而 SAX 解析则不同,它采用边读取边处理的方式操作 XML,逐行扫描 XML 文档,遇到标签时触发解析处理器,进而触发相应的事件 Handler。这种方式内存占用小、效率高,但 POI 官方提供的 API 过于繁琐,使用起来步骤繁多,比如读取一个 Excel 文件,要先将 xlsx 格式的 Excel 文件解析成 OPCPackage 对象,再创建 XSSFReader 对象来解析获取对应 xlsx 下的 xml 内容,想要处理还得进一步创建内容处理器等等,着实有些麻烦。

三、EasyExcel 的原理剖析

(一)核心架构与流程

在 EasyExcel 中,有一个核心的类叫 ExcelAnalyserImpl,它就像是整个操作的调度中心。里面包含了 AnalysisContext 类(分析上下文,存放对应的文件 Inputstream 跟 AnalysisEventListener 事件监听处理器等)和 ExcelReadExecutor 类(默认是 XlsxSaxAnalyser 类,核心方法是 parseXmlSource (),负责逐行 SAX 解析 Excel)。

当 XlsxSaxAnalyser 解析类执行解析方法后,会调用 AnalysisEventProcessor 执行对应的事件方法,而在这个 processor 里真正执行操作的就是对应的事件监听器啦。官方默认提供了一个事件监听器,能把 Excel 解析成 BeanMap 的形式,然后根据我们传入的实体类,返回给我们想要的实体类对象。要是我们有定制化的功能需求,那就需要去了解这个监听器的核心方法了哦。

以下是一个简单的示例代码,展示如何使用 EasyExcel 读取 Excel 文件并将数据转换为自定义对象(假设我们有一个 User 实体类,包含 name 和 age 等属性):

import com.alibaba.excel.EasyExcel;
import com.alibaba.excel.context.AnalysisContext;
import com.alibaba.excel.event.AnalysisEventListener;
import java.io.FileInputStream;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;// 自定义监听器,用于处理读取到的数据
class UserDataListener extends AnalysisEventListener<User> {private List<User> userList = new ArrayList<>();// 每解析一行数据就会调用此方法@Overridepublic void invoke(User user, AnalysisContext analysisContext) {userList.add(user);}// 全部解析完成后调用此方法@Overridepublic void doAfterAllAnalysed(AnalysisContext analysisContext) {// 这里可以对读取到的所有数据进行后续操作,比如存入数据库等System.out.println("共读取到 " + userList.size() + " 条用户数据");}public List<User> getUserList() {return userList;}
}public class EasyExcelReadExample {public static void main(String[] args) throws IOException {String filePath = "your_excel_file_path.xlsx";  // 替换为实际的 Excel 文件路径// 读取 Excel 文件,第二个参数是自定义的监听器EasyExcel.read(new FileInputStream(filePath), User.class, new UserDataListener()).sheet().doRead();}
}
注解

  • 在上述代码中,首先定义了 UserDataListener 类,它继承自 AnalysisEventListener,并重写了 invoke 和 doAfterAllAnalysed 方法。invoke 方法用于在每解析一行 Excel 数据时将其封装成 User 对象并添加到 userList 中,而 doAfterAllAnalysed 方法则在整个 Excel 文件解析完成后执行,可以在这里进行一些后续的数据处理操作,比如将数据批量存入数据库等。
  • 在 EasyExcelReadExample 类的 main 方法中,通过 EasyExcel.read 方法来启动 Excel 文件的读取流程,传入文件输入流、要转换的目标对象类型(这里是 User 类)以及自定义的监听器,然后调用 sheet 和 doRead 方法完成读取操作。

(二)关键方法解析

1. doRead () 方法
doRead () 方法实际调用过程还挺有意思的,它先是调用了 ExcelReader 中的 read 方法与 finish 方法。read 方法实际调用了 Executor 中的 execute 方法,这个 execute 方法里会调用前面提到的核心方法 parseXmlSource 解析 excel,并且在一个 sheet 中所有数据读取完后,会调用事件调度器的 endSheet 方法,让每一个监听器执行对应的 doAfterAllAnalysed 方法。而 finish 方法则负责对读取过程持有容器中流的内容输出,之后清理存储的缓存,把开启的相应的流关闭。
2. doWrite () 方法
doWrite () 方法同样调用了 Writer 中的 write 方法和 finish 方法,这里的 finish 方法作用和读操作里类似哦。write 方法实际调用的是 Builder 中的 addContent 方法,在 addContent 方法里又会调用 Executor 中的 add 方法,针对传入的列表,逐个对象执行 addOneRowOfDataToExcel 方法进行逐行写入。在这个过程中,无论是创建行对象前后,还是填充完数据之后,我们都可以自定义处理器对流程进行相应的处理呢,非常灵活。

以下是一个使用 EasyExcel 写入 Excel 文件的示例代码,假设我们要将一个 List<User> 数据写入到 Excel 中:

import com.alibaba.excel.EasyExcel;
import com.alibaba.excel.write.metadata.WriteSheet;
import java.util.ArrayList;
import java.util.List;class User {private String name;private int age;// 构造函数、Getter 和 Setter 方法省略,可根据实际情况补充完整public User(String name, int age) {this.name = name;this.age = age;}
}public class EasyExcelWriteExample {public static void main(String[] args) {List<User> userList = new ArrayList<>();userList.add(new User("张三", 25));userList.add(new User("李四", 30));String filePath = "output_excel_file.xlsx";  // 输出的 Excel 文件路径// 这里使用 EasyExcel 的 write 方法开始写入操作EasyExcel.write(filePath, User.class).sheet("用户信息表").doWrite(userList);}
}
注解

  • 在这个示例中,先定义了 User 类来表示要写入 Excel 的数据对象,包含 name 和 age 等属性(这里省略了部分常规的方法,实际使用中需补充完整)。
  • 在 EasyExcelWriteExample 类的 main 方法中,创建了一个 List<User> 集合并添加了一些示例数据。然后通过 EasyExcel.write 方法启动写入流程,传入输出文件路径和要写入的数据对象类型(User 类),接着指定 sheet 名称,最后调用 doWrite 方法并传入数据列表,这样就可以将数据成功写入到指定的 Excel 文件中啦。

四、EasyExcel 的性能与易用性优势

(一)性能优势

通过官方给出的效果图可以看到,EasyExcel 仅用 16M 内存在 23 秒内就能读取 75M(46W 行 25 列)的 Excel 文件,相比之下,POI 读取内存要用到 100M 往上了,读取时间更是没法比,可见在性能方面,EasyExcel 是遥遥领先呀。这得益于它基于事件机制逐行扫描数据,对数据逐行处理后,只要对象不被引用,就会被 JVM 快速垃圾回收,从而有效避免了 OOM 问题。

(二)易用性优势

使用 EasyExcel 进行文件的导入导出,相比 POI 的流程那可是简化了一大截呢,只要短短几行代码就可以轻松实现 Excel 的导入导出。这对于咱们开发者来说,简直太友好了,能大大提高开发效率呀。

五、EasyExcel 中的设计模式 个人理解

(一)工厂模式

EasyExcel 里的 EasyExcelFactory 类就运用了工厂模式哦。这个类拥有很多对应方法的不同入参的变体,最终目的都是为了根据不同的入参构造对应的 ExcelWriter/ReaderBuilder 对象,让代码调用起来简洁又美观呢。

(二)观察者模式(也叫发布 - 订阅模式)

通过事件监听器的机制,实现了类似观察者模式的效果。当 Excel 文件解析过程中遇到行、单元格等情况时会触发事件,然后通过自定义监听器来处理数据,各个监听器就像是观察者一样,等待着对应的事件发生然后执行相应的操作。

(三)模板方法模式

在解析和写入等流程中,定义了一些模板化的方法,不同的实现类可以按照这些模板去扩展和定制具体的业务逻辑,保证了整体流程的规范性和可扩展性。

(四)装饰器模式

在写样式等方面运用了装饰器模式,方便我们对 Excel 的样式等进行个性化的装饰和处理,让生成的 Excel 文件更加符合实际业务需求。

六、实际应用案例

在实际项目中,EasyExcel 发挥着巨大的作用呢。比如说,我曾经需要从 Excel 表格中批量导入用户信息到 MySQL 数据库里。如果使用 POI,不仅操作复杂,而且面对稍大一点的 Excel 文件就容易出现内存溢出问题。而选择 EasyExcel 后,它简单易用,性能又优越,更重要的是能够节约内存、解决大文件内存溢出问题。像一个 3M 的 excel 文件,用 POI sax 解析依然需要 100M 左右内存,改用 easyexcel 后可以降低到几 M,而且再大的 excel 文件也不会出现内存溢出啦。对于数据量小的文件,我采用同步模式一次性获取所有表格数据并存储到 List 中;对于数据量大的文件,则采用自定义 Listener 的方式异步逐行读取 Excel 并分批插入到数据库中,非常方便高效。

七、总结

总的来说,EasyExcel 作为一款强大的 Excel 处理组件,在 Apache POI 的基础上进行了优化和封装,无论是在性能、易用性还是功能扩展性上都有着出色的表现。通过运用多种设计模式,让它更加灵活且易于使用,在实际项目中能够帮我们轻松应对各种 Excel 文件的读写需求,大大提高了开发效率,也减少了因为内存溢出等问题带来的烦恼。希望大家在之后的开发工作中,如果遇到 Excel 处理相关的业务,不妨试试 EasyExcel 哦,相信它会给你带来意想不到的惊喜。

以上就是本次关于 EasyExcel 的全部内容分享啦,大家如果有任何疑问或者使用心得,欢迎在评论区留言交流呀。

觉得有用的话可以点点赞 (*/ω\*),支持一下。

如果愿意的话关注一下。会对你有更多的帮助。

每天都会不定时更新哦  >人<  。

相关文章:

深入解析 EasyExcel 组件原理与应用

✨深入解析 EasyExcel 组件原理与应用✨ 官方&#xff1a;EasyExcel官方文档 - 基于Java的Excel处理工具 | Easy Excel 官网 在日常的 Java 开发工作中&#xff0c;处理 Excel 文件的导入导出是极为常见的需求。 今天&#xff0c;咱们就一起来深入了解一款非常实用的操作 Exce…...

JSON数据转化为Excel及数据处理分析

在现代数据处理中&#xff0c;JSON&#xff08;JavaScript Object Notation&#xff09;因其轻量级和易于人阅读的特点而被广泛使用。然而&#xff0c;有时我们需要将这些JSON数据转化为Excel格式以便于进一步的分析和处理。本文将介绍如何将JSON数据转化为Excel文件&#xff0…...

(计算机网络)期末

计算机网络概述 物理层 信源就是发送方 信宿就是接收方 串行通信--一次只发一个单位的数据&#xff08;串行输入&#xff09; 并行通信--一次可以传输多个单位的数据 光纤--利用光的反射进行传输 传输之前&#xff0c;要对信源进行一个编码&#xff0c;收到信息之后要进行一个…...

【AI技术赋能有限元分析应用实践】将FEniCS 软件安装在Ubuntu22.04

FEniCS 完整介绍 FEniCS 是一个开源的计算工具包,专门用于解决偏微分方程(PDE)的建模和求解。它以灵活的数学抽象和高效的计算性能著称,可以让用户使用高层次的数学表达来定义问题,而无需关注底层的数值实现细节。 具体来看,FEniCS 是一个开源的高性能计算工具包,用于…...

快速识别模型:simple_ocr,部署教程

快速识别图片中的英文、标点符号、数学符号、Emoji, 模型会输出图片中文字行的坐标位置、最低得分、识别结果。当前服务用到的模型&#xff1a;检测模型、数字识别、英文符号识别。 一、部署流程 1.更新基础环境 apt update2.安装miniconda wget https://repo.anaconda.com/…...

【C/C++】数据库链接入门教程:从零开始的详细指南!MySQL集成与操作

文章目录 环境配置&#xff1a;搭建开发环境的基础步骤2.1 安装MySQL数据库2.2 配置C/C开发环境2.3 下载并安装MySQL Connector/C 基础操作&#xff1a;实现C/C与MySQL的基本交互3.1 建立数据库连接3.2 执行SQL语句3.3 处理查询结果 进阶技巧&#xff1a;提升数据库操作效率与安…...

C#中面试的常见问题005

1、重载和重写 重载&#xff08;Overloading&#xff09; 重载是指在同一个类中定义多个同名方法&#xff0c;但参数列表不同&#xff08;参数的数量、类型或顺序不同&#xff09;。返回类型可以相同也可以不同。重载方法允许你根据传入的参数类型和数量来调用不同的方法。 …...

使用Redis生成全局唯一id

为了生成一个符合要求的分布式全局ID&#xff0c;我们可以使用 StringRedisTemplate 来实现。这个ID由三部分组成&#xff1a; 符号位&#xff08;1 bit&#xff09;&#xff1a;始终为0&#xff0c;表示正数。时间戳&#xff08;31 bit&#xff09;&#xff1a;表示从某个起始…...

pnpm:包管理的新星,平替 npm 和 yarn

​ pnpm&#xff0c;一个老牌的 node.js 包管理器&#xff0c;支持 npm 的所有功能&#xff0c;完全足以用来替代 npm。它采用全局存储&#xff0c;每个项目内部使用了硬链接&#xff0c;所以很省空间&#xff0c;安装速度快。 本文介绍下 pnpm 的基本概念&#xff0c;安装、…...

Android调起系统分享图片到其他应用

Android调起系统分享图片到其他应用 有时候分享不想接第三方的&#xff0c;其实如果你的分享要求不是很高&#xff0c;调系统的分享也是可以的。 一、思路&#xff1a; 用intent.action Intent.ACTION_SEND 二、效果图&#xff1a; 三、关键代码&#xff1a; //这个是分享…...

详解Qt QBuffer

文章目录 **QBuffer 的详解****前言****QBuffer 是什么&#xff1f;****QBuffer 的主要用途****构造函数****主要成员函数详解****1. open()****原型&#xff1a;****作用&#xff1a;****参数&#xff1a;****返回值&#xff1a;****示例代码&#xff1a;** **2. write()****原…...

Python基础学习-11函数参数

1、"值传递” 和“引用传递” 1&#xff09;不可变的参数通过“值传递”。比如整数、字符串等 2&#xff09;可变的参数通过“引用参数”。比如列表、字典。 3&#xff09;避免可变参数的修改 4&#xff09;内存模型简介 2、函数参数类型 1&#xff09; def func() #无参…...

GTK#框架让C# Winform程序跨平台运行

在软件开发领域&#xff0c;跨平台能力是一个重要的考量因素。对于C#开发者来说&#xff0c;Winform是构建桌面应用的强大工具&#xff0c;但原生Winform只支持Windows平台。幸运的是&#xff0c;GTK#框架的出现让C# Winform程序跨平台运行成为可能。本文将详细介绍如何使用GTK…...

在Kubernetes使用CronJob实现定时删除指定天数外的文件(我这里使用删除备份mysql数据库文件为例)

文章目录 一、代码使用方式1、golang代码2、使用方法二、容器镜像使用方式1、制作镜像2、我公开的镜像3、使用方法一、代码使用方式 1、golang代码 vim cleanfile.go package mainimport ("flag""fmt""io/ioutil""os""path/fi…...

使用 Elastic 收集 Windows 遥测数据:ETW Filebeat 输入简介

作者&#xff1a;来自 Elastic Chema Martinez 在安全领域&#xff0c;能够使用 Windows 主机的系统遥测数据为监控、故障排除和保护 IT 环境开辟了新的可能性。意识到这一点&#xff0c;Elastic 推出了专注于 Windows 事件跟踪 (ETW) 的新功能 - 这是一种强大的 Windows 原生机…...

力扣-位运算-4【算法学习day.44】

前言 ###我做这类文章一个重要的目的还是给正在学习的大家提供方向和记录学习过程&#xff08;例如想要掌握基础用法&#xff0c;该刷哪些题&#xff1f;&#xff09;我的解析也不会做的非常详细&#xff0c;只会提供思路和一些关键点&#xff0c;力扣上的大佬们的题解质量是非…...

Stable Diffusion 3详解

&#x1f33a;系列文章推荐&#x1f33a; 扩散模型系列文章正在持续的更新&#xff0c;更新节奏如下&#xff0c;先更新SD模型讲解&#xff0c;再更新相关的微调方法文章&#xff0c;敬请期待&#xff01;&#xff01;&#xff01;&#xff08;本文及其之前的文章均已更新&…...

c#异步编程(async/await)

注&#xff1a;下文摘自ChatGPT&#xff0c;总结与案例都非常完善&#xff0c;可以快速理解并应用 0&#xff1a;使用场景 在winform界面程序中&#xff0c;在ui操作中涉及到一些耗时的等待操作&#xff0c;使用线程自己处理已经显得力不从心&#xff0c;如何能更好的实现&am…...

TCP/IP学习笔记

TCP\IP从实际应用的五层结构开始&#xff0c;自顶而下的去分析每一层。 TCP/IP五层架构概述 学术上面是TCP/IP四层架构&#xff0c;OSI/ISO是七层架构&#xff0c;实际中使用的是TCP/IP五层架构。 数据链路层 ICMP数据包分析 Wireshark抓包分析ICMP协议_wireshark抓ping包分析…...

0000_vim自定义快捷键_alias

vim自定义快捷键_alias 如下&#xff1a; 1.直接打开vi ~/.bashrc 然后到最底部&#xff0c;添加alias快捷键 2.添加alias快捷键mgplat 以后只要发送mgplat就等于出发了那么长一条指令 3.保存退出即可 【注意】 操作完后&#xff0c;可能你用mgplat无法使用&#xff0c;可…...

Spring Boot项目中,实体类是否需要实现Serializable接口

在Spring Boot项目中&#xff0c;实体类是否需要实现Serializable接口并不是一个硬性规定&#xff0c;而是取决于具体的应用场景和需求。以下是对这一问题的更详细分析&#xff1a; 1. 序列化的基本概念 序列化是将对象的状态信息转换为可以存储或传输的形式的过程。反序列化则…...

打通工业通信壁垒实现Ethernetip转profinet网络互通

西门子S7-1500 PLC&#xff08;profinet&#xff09;与AB PLC 1769-L32E以太网通讯&#xff08;EtherNet/IP&#xff09;。今天与大家分享一篇Profinet转EtherNet/IP的通讯配置方案。本文主要介绍开疆智能的Profinet转EtherNet/IP网关KJ-PNG-208&#xff0c;连接西门子S7-1500 …...

数据结构_图的应用

最小生成树 Prim算法 int AMGraph::sum(string v) {int start, totalW, cnt, minW, u, vv, i, j;start LocateVex(v); // 获取起始顶点编号memset(visited, false, sizeof(visited)); // 初始化访问状态visited[start] true;totalW 0; // 最小生成树的总权重cnt 1; // 当前…...

C#中面试的常见问题002

1.wpf和Winfrom的区别 1. 技术基础 WPF&#xff1a;基于.NET Framework&#xff0c;使用XAML&#xff08;可扩展应用程序标记语言&#xff09;作为界面描述语言&#xff0c;支持矢量图形和高级布局。WinForms&#xff1a;基于.NET Framework&#xff0c;使用纯代码或拖放设计…...

快速理解微服务中Ribbon的概念

一.基本概念 1.在微服务架构中&#xff0c;Ribbon 是一个客户端负载均衡器&#xff0c;用于控制服务间的通信方式。 2.Ribbon 是一个开源的库&#xff0c;最早由 Netflix 开发&#xff0c;用于实现客户端负载均衡。 3.Ribbon 主要解决的是在微服务架构中&#xff0c;多个服务…...

K8S简介、使用教程

以下是关于 Kubernetes&#xff08;通常缩写为 K8S&#xff09;的简介和使用教程&#xff1a; 一、Kubernetes 简介 定义与作用 Kubernetes 是一个开源的容器编排平台&#xff0c;用于自动化部署、扩展和管理容器化应用程序。它最初由谷歌开发&#xff0c;后捐赠给云原生计算基…...

极狐GitLab 17.6 正式发布几十项与 DevSecOps 相关的功能【四】

GitLab 是一个全球知名的一体化 DevOps 平台&#xff0c;很多人都通过私有化部署 GitLab 来进行源代码托管。极狐GitLab 是 GitLab 在中国的发行版&#xff0c;专门为中国程序员服务。可以一键式部署极狐GitLab。 学习极狐GitLab 的相关资料&#xff1a; 极狐GitLab 官网极狐…...

麦肯锡报告 | 科技落地的真谛:超越技术本身的价值创造

科技创新正在以惊人的速度改变企业运作和客户体验&#xff0c;但实现其潜力的关键在于正确的策略、流程、文化和人才。麦肯锡强调了一个理念&#xff1a;Never just tech&#xff08;不仅仅是技术&#xff09;。这表明&#xff0c;成功的数字化转型不仅依赖于技术&#xff0c;还…...

彻底解决 macOS 下Matplotlib 中文显示乱码问题

彻底解决 macOS 下Matplotlib 中文显示乱码问题 在使用 Python 的 Matplotlib 库进行数据可视化时&#xff0c;中文字符的显示常常会出现乱码问题&#xff0c;尤其在 macOS 系统上。在网上找了一大堆方法&#xff0c;花了很久&#xff0c;发现不是要安装各种字体就是要改配置&…...

STM32-- keil 的option for target使用

keil版本号 1.device界面 如&#xff1a;stm32f103c8t6的工程&#xff0c;可以直接在device这里修改成stm32f103vct6&#xff0c;虽然引脚不一样&#xff0c;但是很多一样的地方&#xff0c;可以直接使用&#xff0c;有些不修改也可以下载程序。 2.target xtal的设置不起作用了…...

什么网站做任务赚钱/制作网站需要什么软件

一、测试数据&#xff1a;手机上网日志1.1 日志假设我们如下一个日志文件&#xff0c;这个文件的内容是来自某个电信运营商的手机上网日志&#xff0c;文件的内容已经经过了优化&#xff0c;格式比较规整&#xff0c;便于学习研究。每一行不同的字段又有不同的含义&#xff0c;…...

小蜜蜂网站建设/合肥百度推广优化排名

题目 题目&#xff1a; 1.分别使用*/运算&#xff0c;结果都是8 2.把你的幸运数字存储在一个变量中&#xff0c;再用这个变量说出你的心愿。并打印出来 3.添加注释 以下是本篇文章正文内容&#xff0c;欢迎朋友们进行指正&#xff0c;一起探讨&#xff0c;共同进步。——来自考…...

个人博客网站总结/app运营方案

refurl:http://book.51cto.com/art/201004/193852.htm...

做慕斯蛋糕那个网站有视频/北京互联网公司

动态变量和静态变量的区别&#xff1a; 1、存储位置动态变量&#xff1a;存储在内存出栈数据区静态变量&#xff1a;存储在全局数据区&#xff08;静态数据区&#xff09; 2、生命期动态变量&#xff1a;根据你定义的位置确定&#xff0c;比如你在一个函数中定义的&#xff0c;…...

dreamweaver网站建设与管理心得/重庆网站关键词排名优化

每个拼多多店铺都是有自己的动态评分的&#xff0c;如果拼多多动态评分越高的话&#xff0c;说明这个店铺运营的越好&#xff0c;但如果评分很低的话&#xff0c;店铺会被限制很多。拼多多DSR到了多少不能参加活动&#xff1f; 一、拼多多dsr到了多少不能参加活动&#xff1f; …...

做招生网站/长春网站快速排名提升

upx upx加壳脱壳程序 upx -d 脱壳 objdump -d 反编译整个程序 readelf -r target_elf objdump -R target_elf 查看GOT表中的内容...