如何使用EasyExcel进行跨Sheet的数据操作

2025-04发布8次浏览

EasyExcel 是阿里巴巴开源的一个基于 Java 的 Excel 处理库,它提供了简单易用的 API 来读取和写入 Excel 文件。在实际业务场景中,我们经常需要对同一个 Excel 文件中的多个 Sheet 进行数据操作,比如从一个 Sheet 中读取数据并写入到另一个 Sheet 中,或者跨 Sheet 进行数据校验等。

本文将详细介绍如何使用 EasyExcel 进行跨 Sheet 的数据操作,并提供具体的代码示例和流程说明。


1. 跨 Sheet 数据操作的基本概念

在 Excel 文件中,一个文件可以包含多个 Sheet(工作表)。每个 Sheet 可以独立存储数据,但有时我们需要在这些 Sheet 之间进行数据交互或处理。例如:

  • Sheet 数据复制:将一个 Sheet 的数据复制到另一个 Sheet。
  • Sheet 数据关联:根据某些条件,将一个 Sheet 的数据与另一个 Sheet 的数据进行匹配或关联。
  • Sheet 数据校验:检查不同 Sheet 之间的数据是否一致。

EasyExcel 提供了灵活的 API 来支持这些操作。


2. 实现跨 Sheet 数据操作的步骤

2.1 准备工作

首先确保项目中已引入 EasyExcel 的依赖。Maven 配置如下:

<dependency>
    <groupId>com.alibaba</groupId>
    <artifactId>easyexcel</artifactId>
    <version>3.0.5</version>
</dependency>

2.2 创建 Excel 模型类

为了简化数据读写操作,我们可以为每个 Sheet 定义对应的模型类。假设我们有一个 Excel 文件,其中包含两个 Sheet:Sheet1Sheet2

  • Sheet1 存储用户信息(如 ID、姓名)。
  • Sheet2 存储订单信息(如 用户ID、订单号)。

定义模型类如下:

// Sheet1 对应的模型类
@Data
public class User {
    private Integer id;
    private String name;
}

// Sheet2 对应的模型类
@Data
public class Order {
    private Integer userId;
    private String orderNo;
}

2.3 读取多个 Sheet 的数据

EasyExcel 支持通过监听器来逐行读取数据。我们可以定义一个自定义监听器,用于分别读取 Sheet1Sheet2 的数据。

public class UserListener extends AnalysisEventListener<User> {
    private List<User> users = new ArrayList<>();

    @Override
    public void invoke(User user, AnalysisContext context) {
        users.add(user);
    }

    @Override
    public void doAfterAllAnalysed(AnalysisContext context) {
        // 所有数据解析完成后执行
    }

    public List<User> getUsers() {
        return users;
    }
}

public class OrderListener extends AnalysisEventListener<Order> {
    private List<Order> orders = new ArrayList<>();

    @Override
    public void invoke(Order order, AnalysisContext context) {
        orders.add(order);
    }

    @Override
    public void doAfterAllAnalysed(AnalysisContext context) {
        // 所有数据解析完成后执行
    }

    public List<Order> getOrders() {
        return orders;
    }
}

2.4 使用 EasyExcel 读取数据

接下来,我们可以使用 EasyExcel 的 ExcelReader 类来读取多个 Sheet 的数据。

import com.alibaba.excel.EasyExcel;
import com.alibaba.excel.ExcelReader;
import com.alibaba.excel.read.listener.ReadListener;

import java.util.List;

public class CrossSheetExample {
    public static void main(String[] args) {
        String fileName = "example.xlsx";

        // 创建监听器实例
        UserListener userListener = new UserListener();
        OrderListener orderListener = new OrderListener();

        // 创建 ExcelReader 并指定要读取的 Sheet
        ExcelReader excelReader = EasyExcel.read(fileName)
                .head(User.class) // 设置第一个 Sheet 的头信息
                .sheet(0) // 读取第一个 Sheet
                .build();

        // 读取第一个 Sheet 的数据
        excelReader.read(new ReadListener[]{userListener});

        // 切换到第二个 Sheet
        excelReader.sheet(1) // 读取第二个 Sheet
                .head(Order.class) // 设置第二个 Sheet 的头信息
                .doRead(orderListener);

        // 获取读取的数据
        List<User> users = userListener.getUsers();
        List<Order> orders = orderListener.getOrders();

        // 输出结果
        System.out.println("Users: " + users);
        System.out.println("Orders: " + orders);

        // 关闭 Reader
        excelReader.finish();
    }
}

2.5 数据关联与校验

假设我们需要检查每个订单是否都有对应的用户。可以通过遍历 ordersusers 列表来实现。

for (Order order : orders) {
    boolean userExists = false;
    for (User user : users) {
        if (order.getUserId().equals(user.getId())) {
            userExists = true;
            break;
        }
    }
    if (!userExists) {
        System.out.println("Order " + order.getOrderNo() + " has no corresponding user.");
    }
}

3. 流程图描述

以下是跨 Sheet 数据操作的整体流程图:

graph TD
    A[加载 Excel 文件] --> B[创建 ExcelReader]
    B --> C[读取第一个 Sheet 数据]
    C --> D[解析并存储数据]
    D --> E[切换到第二个 Sheet]
    E --> F[读取第二个 Sheet 数据]
    F --> G[解析并存储数据]
    G --> H[关闭 Reader]
    H --> I[数据关联与校验]

4. 注意事项

  1. 性能优化:如果 Excel 文件非常大,建议使用分页读取或流式读取,避免一次性加载过多数据导致内存溢出。
  2. 异常处理:在实际应用中,应对可能出现的异常(如文件格式错误、数据缺失等)进行捕获和处理。
  3. 多线程支持:EasyExcel 支持多线程读取,可以根据需求配置线程数以提高效率。