Java实现Excel转JSON的代码详解
使用Java结合FreeSpire XLS库可自动将Excel转为JSON,通过读取工作表并映射为键值对,高效支持数据迁移、报表导出与系统对接,大幅提升效率并消除手动录入错误。
在企业数据整合与系统对接的日常中,Excel 文件几乎是无处不在的数据载体。但说到真正要把这些表格里的业务数据喂给 Web 应用、移动端或者微服务接口时,Excel 那套二进制格式就显得有些格格不入——直接传输和解析都不太现实。而 JSON 作为轻量级数据交换格式,早已是 API 通信和数据存储的事实标准。手动把 Excel 数据一条条录入 JSON?效率低不说,还特别容易出岔子,数据量一大或者文件一多就更是灾难。

所以,用编程的方式自动完成 Excel 到 JSON 的转换,就成了最合理的方案。它能批量提取数据,把行列结构映射成标准的键值对,然后直接给 RESTful API 用、存进数据库,或者让前端页面拿来就用。
这篇文章就来聊聊,怎么用 Ja va 从 Excel 文件里读数据,再转成结构化的 JSON 格式输出。整个过程高度自动化,特别适合数据迁移、报表导出、系统对接这类场景。
文章中用到的是 Free Spire.XLS for Ja va,通过 Ma ven 引入即可:
com.e-iceblue e-iceblue https://repo.e-iceblue.cn/repository/ma ven-public/ e-iceblue spire.xls.free 16.3.1
1. 创建示例 Excel 文件
为了完整走通整个流程,我们先创建一个包含员工信息的 Excel 文件,模拟企业里常见的人力资源数据表:
import com.spire.xls.*;
public class CreateSampleExcel {
public static void main(String[] args) {
// 1 创建工作簿并获取第一个工作表
Workbook workbook = new Workbook();
Worksheet sheet = workbook.getWorksheets().get(0);
sheet.setName("员工信息");
// 2 写入表头
sheet.get(1, 1).setText("员工编号");
sheet.get(1, 2).setText("姓名");
sheet.get(1, 3).setText("部门");
sheet.get(1, 4).setText("职位");
sheet.get(1, 5).setText("入职日期");
sheet.get(1, 6).setText("月薪(元)");
// 设置表头加粗
for (int col = 1; col <= 6; col++) {
sheet.get(1, col).getStyle().getFont().isBold(true);
}
// 3 写入员工数据
sheet.get(2, 1).setText("EMP001");
sheet.get(2, 2).setText("张三");
sheet.get(2, 3).setText("技术部");
sheet.get(2, 4).setText("高级工程师");
sheet.get(2, 5).setText("2019-03-15");
sheet.get(2, 6).setNumberValue(18000);
sheet.get(3, 1).setText("EMP002");
sheet.get(3, 2).setText("李四");
sheet.get(3, 3).setText("市场部");
sheet.get(3, 4).setText("市场经理");
sheet.get(3, 5).setText("2020-07-01");
sheet.get(3, 6).setNumberValue(15000);
sheet.get(4, 1).setText("EMP003");
sheet.get(4, 2).setText("王五");
sheet.get(4, 3).setText("财务部");
sheet.get(4, 4).setText("财务主管");
sheet.get(4, 5).setText("2018-11-20");
sheet.get(4, 6).setNumberValue(16500);
sheet.get(5, 1).setText("EMP004");
sheet.get(5, 2).setText("赵六");
sheet.get(5, 3).setText("人事部");
sheet.get(5, 4).setText("HR专员");
sheet.get(5, 5).setText("2021-05-10");
sheet.get(5, 6).setNumberValue(12000);
sheet.get(6, 1).setText("EMP005");
sheet.get(6, 2).setText("孙七");
sheet.get(6, 3).setText("技术部");
sheet.get(6, 4).setText("前端开发");
sheet.get(6, 5).setText("2022-01-08");
sheet.get(6, 6).setNumberValue(14000);
// 4 自动调整列宽
sheet.getAllocatedRange().autoFitColumns();
// 5 保存文件
String outputFile = "EmployeeData.xlsx";
workbook.sa veToFile(outputFile, ExcelVersion.Version2013);
workbook.dispose();
System.out.println("Excel 文件已创建:" + outputFile);
}
}
说明:
Workbook创建新的 Excel 工作簿对象,默认有三个工作表getWorksheets().get(0)获取第一个工作表get(row, col)通过行列索引访问指定单元格setText()设置文本类型数据,setNumberValue()设置数值类型数据getStyle().getFont().isBold(true)设置单元格字体加粗getAllocatedRange().autoFitColumns()自动调整所有列宽
这一步生成的文件里有 5 名员工信息,后续的 JSON 转换就用它当源数据。
2. 将整个工作表转换为 JSON 数组
接下来,加载刚才的 Excel 文件,把每一行数据映射成一个 JSON 对象,第一行自动作为字段名(键名),最终输出为一个 JSON 数组:
import com.spire.xls.*;
import com.spire.data.table.DataTable;
public class ExcelToJsonArray {
public static void main(String[] args) {
String inputFile = "EmployeeData.xlsx";
String outputFile = "EmployeeData.json";
// 1 加载 Excel 文件
Workbook workbook = new Workbook();
workbook.loadFromFile(inputFile);
// 2 获取第一个工作表
Worksheet sheet = workbook.getWorksheets().get(0);
// 3 将工作表数据导出为 DataTable
DataTable dataTable = sheet.exportDataTable();
int rowCount = dataTable.getRows().size();
int colCount = dataTable.getColumns().size();
// 4 构建 JSON 数组
StringBuilder jsonBuilder = new StringBuilder();
jsonBuilder.append("[\n");
for (int i = 0; i < rowCount; i++) {
jsonBuilder.append(" {\n");
for (int j = 0; j < colCount; j++) {
String columnName = dataTable.getColumns().get(j).getCaption();
String cellValue = dataTable.getRows().get(i).getString(j);
// 判断值是否为数值类型,决定是否加引号
jsonBuilder.append(" \"").append(escapeJson(columnName)).append("\": ");
if (isNumeric(cellValue)) {
jsonBuilder.append(cellValue);
} else {
jsonBuilder.append("\"").append(escapeJson(cellValue)).append("\"");
}
if (j < colCount - 1) {
jsonBuilder.append(",");
}
jsonBuilder.append("\n");
}
jsonBuilder.append(" }");
if (i < rowCount - 1) {
jsonBuilder.append(",");
}
jsonBuilder.append("\n");
}
jsonBuilder.append("]");
// 5 写入 JSON 文件
try (ja va.io.FileWriter writer = new ja va.io.FileWriter(outputFile)) {
writer.write(jsonBuilder.toString());
} catch (Exception e) {
e.printStackTrace();
}
workbook.dispose();
System.out.println("JSON 文件已生成:" + outputFile);
}
// 判断字符串是否为数值
private static boolean isNumeric(String str) {
if (str == null || str.isEmpty()) return false;
try {
Double.parseDouble(str);
return true;
} catch (NumberFormatException e) {
return false;
}
}
// 转义 JSON 特殊字符
private static String escapeJson(String value) {
if (value == null) return "";
return value.replace("\\", "\\\\")
.replace("\"", "\\\"")
.replace("\n", "\\n")
.replace("\r", "\\r")
.replace("\t", "\\t");
}
}
说明:
loadFromFile()从磁盘加载 Excel 文件exportDataTable()将整个工作表导出为DataTable,第一行自动作为列名getColumns().get(j).getCaption()获取列名作为 JSON 的键名getRows().get(i).getString(j)获取指定行列的单元格值isNumeric()辅助判断是否为数值,数值类型在 JSON 中不加引号escapeJson()处理 JSON 特殊字符的转义,保证输出格式正确
转换结果:
[
{
"员工编号": "EMP001",
"姓名": "张三",
"部门": "技术部",
"职位": "高级工程师",
"入职日期": "2019-03-15",
"月薪(元)": 18000.0
},
{
"员工编号": "EMP002",
"姓名": "李四",
"部门": "市场部",
"职位": "市场经理",
"入职日期": "2020-07-01",
"月薪(元)": 15000.0
}
]
以上仅展示前两条记录,完整输出包含全部 5 名员工数据。每条记录以表头中文作为 JSON 键名,数值类型字段不加引号。
3. 将指定区域数据转换为 JSON 对象
实际项目中,工作表里经常会有标题行、汇总行这类额外信息。我们往往会手痒想跳过它们,只提取特定区域的数据,再顺便加一些文档级元信息,生成更丰富的嵌套 JSON 结构。下面这个例子就演示了这种玩法:
import com.spire.xls.*;
import com.spire.data.table.DataTable;
import com.spire.xls.ExportTableOptions;
public class ExcelToNestedJson {
public static void main(String[] args) {
String inputFile = "EmployeeData.xlsx";
String outputFile = "EmployeeReport.json";
// 1 加载 Excel 文件
Workbook workbook = new Workbook();
workbook.loadFromFile(inputFile);
// 2 获取第一个工作表
Worksheet sheet = workbook.getWorksheets().get(0);
// 3 使用 ExportTableOptions 配置导出选项
ExportTableOptions options = new ExportTableOptions();
options.setKeepDataFormat(true);
// 从第2行开始导出(跳过表头),导出到最后一个数据行和列
int startRow = 2;
int startCol = 1;
int endRow = sheet.getLastDataRow();
int endCol = sheet.getLastDataColumn();
DataTable dataTable = sheet.exportDataTable(startRow, startCol, endRow, endCol, options);
int rowCount = dataTable.getRows().size();
int colCount = dataTable.getColumns().size();
// 4 手动定义字段映射(列名 → JSON 键名)
String[] fieldNames = {"employeeId", "name", "department", "position", "hireDate", "salary"};
// 5 构建嵌套 JSON 结构
StringBuilder json = new StringBuilder();
json.append("{\n");
json.append(" \"report_name\": \"员工信息报表\",\n");
json.append(" \"sheet_name\": \"").append(sheet.getName()).append("\",\n");
json.append(" \"total_records\": ").append(rowCount).append(",\n");
json.append(" \"employees\": [\n");
for (int i = 0; i < rowCount; i++) {
json.append(" {\n");
for (int j = 0; j < colCount; j++) {
String key = (j < fieldNames.length) ? fieldNames[j] : "field_" + j;
String value = dataTable.getRows().get(i).getString(j);
json.append(" \"").append(key).append("\": ");
if (isNumeric(value)) {
json.append(value);
} else {
json.append("\"").append(escapeJson(value)).append("\"");
}
if (j < colCount - 1) {
json.append(",");
}
json.append("\n");
}
json.append(" }");
if (i < rowCount - 1) {
json.append(",");
}
json.append("\n");
}
json.append(" ]\n");
json.append("}");
// 6 写入 JSON 文件
try (ja va.io.FileWriter writer = new ja va.io.FileWriter(outputFile)) {
writer.write(json.toString());
} catch (Exception e) {
e.printStackTrace();
}
workbook.dispose();
System.out.println("嵌套 JSON 已生成:" + outputFile);
}
private static boolean isNumeric(String str) {
if (str == null || str.isEmpty()) return false;
try {
Double.parseDouble(str);
return true;
} catch (NumberFormatException e) {
return false;
}
}
private static String escapeJson(String value) {
if (value == null) return "";
return value.replace("\\", "\\\\")
.replace("\"", "\\\"")
.replace("\n", "\\n")
.replace("\r", "\\r")
.replace("\t", "\\t");
}
}
说明:
ExportTableOptions里setKeepDataFormat(true)能保留原始数据格式,比如日期、百分比这类。getLastDataRow()和getLastDataColumn()自动获取数据区域边界,省去手工计算。exportDataTable(startRow, startCol, endRow, endCol, options)导出一块矩形区域的数据。- 自定义
fieldNames数组,把 Excel 列名映射成英文驼峰命名,更符合 API 接口规范。 - 输出结构里加了
report_name、sheet_name、total_records这些元信息,形成嵌套结构。
转换结果:
{
"report_name": "员工信息报表",
"sheet_name": "员工信息",
"total_records": 5,
"employees": [
{
"employeeId": "EMP001",
"name": "张三",
"department": "技术部",
"position": "高级工程师",
"hireDate": "2019-03-15",
"salary": 18000.0
},
{
"employeeId": "EMP002",
"name": "李四",
"department": "市场部",
"position": "市场经理",
"hireDate": "2020-07-01",
"salary": 15000.0
}
]
}
以上仅展示前两条员工记录。输出结构包含文档级元信息,字段名采用英文驼峰命名,直接拿来做 API 响应很合适。
4. 批量转换多工作表为 JSON
如果 Excel 文件里塞了好几个工作表,一个遍历循环就能把所有数据全抓出来,打包到一个 JSON 文件里。代码实现也很直白:
import com.spire.xls.*;
import com.spire.data.table.DataTable;
public class MultiSheetToJson {
public static void main(String[] args) {
String inputFile = "MultiSheetData.xlsx";
String outputFile = "AllSheetsData.json";
// 1 创建包含多个工作表的 Excel 文件
Workbook sourceWorkbook = new Workbook();
// 第一个工作表 - 销售数据
Worksheet sheet1 = sourceWorkbook.getWorksheets().get(0);
sheet1.setName("销售数据");
sheet1.get(1, 1).setText("产品");
sheet1.get(1, 2).setText("销量");
sheet1.get(1, 3).setText("销售额");
sheet1.get(2, 1).setText("笔记本电脑");
sheet1.get(2, 2).setNumberValue(1250);
sheet1.get(2, 3).setNumberValue(6250000);
sheet1.get(3, 1).setText("平板电脑");
sheet1.get(3, 2).setNumberValue(890);
sheet1.get(3, 3).setNumberValue(2670000);
// 第二个工作表 - 库存数据
Worksheet sheet2 = sourceWorkbook.getWorksheets().add("库存数据");
sheet2.get(1, 1).setText("产品");
sheet2.get(1, 2).setText("库存数量");
sheet2.get(1, 3).setText("仓库位置");
sheet2.get(2, 1).setText("笔记本电脑");
sheet2.get(2, 2).setNumberValue(350);
sheet2.get(2, 3).setText("A区-01");
sheet2.get(3, 1).setText("平板电脑");
sheet2.get(3, 2).setNumberValue(280);
sheet2.get(3, 3).setText("B区-03");
sourceWorkbook.sa veToFile(inputFile, ExcelVersion.Version2013);
sourceWorkbook.dispose();
// 2 加载并遍历所有工作表
Workbook workbook = new Workbook();
workbook.loadFromFile(inputFile);
StringBuilder json = new StringBuilder();
json.append("{\n");
int sheetCount = workbook.getWorksheets().getCount();
for (int s = 0; s < sheetCount; s++) {
Worksheet sheet = workbook.getWorksheets().get(s);
String sheetName = sheet.getName();
DataTable dataTable = sheet.exportDataTable();
int rowCount = dataTable.getRows().size();
int colCount = dataTable.getColumns().size();
json.append(" \"").append(escapeJson(sheetName)).append("\": [\n");
for (int i = 0; i < rowCount; i++) {
json.append(" {\n");
for (int j = 0; j < colCount; j++) {
String key = dataTable.getColumns().get(j).getCaption();
String value = dataTable.getRows().get(i).getString(j);
json.append(" \"").append(escapeJson(key)).append("\": ");
if (isNumeric(value)) {
json.append(value);
} else {
json.append("\"").append(escapeJson(value)).append("\"");
}
if (j < colCount - 1) json.append(",");
json.append("\n");
}
json.append(" }");
if (i < rowCount - 1) json.append(",");
json.append("\n");
}
json.append(" ]");
if (s < sheetCount - 1) json.append(",");
json.append("\n");
}
json.append("}");
// 3 写入 JSON 文件
try (ja va.io.FileWriter writer = new ja va.io.FileWriter(outputFile)) {
writer.write(json.toString());
} catch (Exception e) {
e.printStackTrace();
}
workbook.dispose();
System.out.println("多工作表 JSON 已生成:" + outputFile);
}
private static boolean isNumeric(String str) {
if (str == null || str.isEmpty()) return false;
try {
Double.parseDouble(str);
return true;
} catch (NumberFormatException e) {
return false;
}
}
private static String escapeJson(String value) {
if (value == null) return "";
return value.replace("\\", "\\\\")
.replace("\"", "\\\"")
.replace("\n", "\\n")
.replace("\r", "\\r")
.replace("\t", "\\t");
}
}
说明:
getWorksheets().getCount()获取工作表总数getWorksheets().add("名称")添加新工作表- 每个工作表的数据以工作表名为键,组织成 JSON 对象的属性
- 适用于多维度数据汇总,比如销售、库存、财务放在不同工作表的情况
输出结果示例:
{
"销售数据": [
{
"产品": "笔记本电脑",
"销量": 1250.0,
"销售额": 6250000.0
},
{
"产品": "平板电脑",
"销量": 890.0,
"销售额": 2670000.0
}
],
"库存数据": [
{
"产品": "笔记本电脑",
"库存数量": 350.0,
"仓库位置": "A区-01"
},
{
"产品": "平板电脑",
"库存数量": 280.0,
"仓库位置": "B区-03"
}
]
}
每个工作表的数据以工作表名称为键,独立组织为 JSON 数组,便于按业务维度分别消费。
- 企业月度综合报表,将不同维度的数据统一输出为 JSON
- 项目管理系统中多工作表数据的统一接口响应
- 跨部门数据汇总,将各部门独立工作表合并为统一数据格式
5. 关键类与方法解析
核心类说明
Workbook 类
Workbook 是 Excel 操作的入口,代表一个完整的 Excel 文件。
常用方法:
| 方法 | 说明 |
|---|---|
new Workbook() | 创建新的工作簿实例 |
loadFromFile(path) | 从指定路径加载 Excel 文件 |
sa veToFile(path, version) | 保存工作簿为 Excel 文件 |
getWorksheets() | 获取工作簿中的所有工作表集合 |
dispose() | 释放工作簿占用的资源 |
Worksheet 类
Worksheet 代表单个工作表,是数据操作的主要对象。
常用方法与属性:
| 方法 / 属性 | 说明 |
|---|---|
get(row, col) | 通过行列索引获取指定单元格 |
getRange() | 获取单元格范围对象 |
getCellRange(row1, col1, row2, col2) | 获取指定矩形区域的单元格范围 |
getName() / setName(name) | 获取或设置工作表名称 |
exportDataTable() | 将整个工作表导出为 DataTable |
exportDataTable(startRow, startCol, endRow, endCol, options) | 导出指定区域为 DataTable |
getLastDataRow() | 获取最后一行数据的行号 |
getLastDataColumn() | 获取最后一列数据的列号 |
getAllocatedRange().autoFitColumns() | 自动调整所有列宽 |
DataTable 类
DataTable 用于存储从工作表导出的表格数据。
常用方法与属性:
| 方法 / 属性 | 说明 |
|---|---|
getRows() | 获取数据行集合 |
getRows().size() | 获取数据行数 |
getRows().get(i).getString(j) | 获取第 i 行第 j 列的值(字符串) |
getColumns() | 获取数据列集合 |
getColumns().size() | 获取数据列数 |
getColumns().get(j).getCaption() | 获取第 j 列的列名 |
ExportTableOptions 类
ExportTableOptions 用于配置数据导出选项。
常用属性:
| 属性 | 说明 |
|---|---|
setKeepDataFormat(boolean) | 是否保留原始数据格式 |
setRenameStrategy(strategy) | 设置列名重复时的重命名策略 |
使用建议:
- 如果原始 Excel 包含日期、百分比等特殊格式,建议开启
setKeepDataFormat(true) - 对于简单的文本和数值数据,直接用无参
exportDataTable()就可以
总结
从创建示例数据、整体工作表转换,到指定区域的嵌套结构输出,再到多工作表的批量处理——用 Ja va 搞定 Excel 转 JSON 这件事,已经都在这篇文章里了。整个过程高度自动化,尤其适合数据迁移、API 对接、报表导出这类场景。
跟手动复制粘贴或依赖在线转换工具比起来,基于 Ja va 代码的方式优势很明显:灵活性强,可以自定义 JSON 结构、字段映射和输出格式;批量处理效率高,多工作表、多文件都能自动搞定;数据可控,能选择性提取特定区域,过滤无关内容;而且很容易集成到 Spring Boot 等 Ja va 框架中,作为数据接口的一部分。
在此基础上,你还可以做更多扩展,比如结合 Gson 或 Jackson 库生成更规范的 JSON、添加数据过滤与清洗逻辑,甚至集成到 RESTful API 中实现实时数据查询。如果你正在处理 Excel 数据的结构化提取或者系统对接需求,这套方案应该能帮上大忙。
游乐网为非赢利性网站,所展示的游戏/软件/文章内容均来自于互联网或第三方用户上传分享,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系youleyoucom@outlook.com。
同类文章
IDEA中SpringBoot项目热部署实现指南
Springboot项目在IDEA中实现热部署需依次完成:开启自动编译(静态与动态编译)、启用热部署策略、引入spring-boot-devtools依赖、关闭浏览器缓存,最后启动测试即可生效,省去手动重启时间,大幅提升开发效率。
Java实现Excel转JSON的代码详解
使用Java结合FreeSpire XLS库可自动将Excel转为JSON,通过读取工作表并映射为键值对,高效支持数据迁移、报表导出与系统对接,大幅提升效率并消除手动录入错误。
Golang高效布谷鸟过滤器多字符集字符串过滤
布谷鸟过滤器支持删除操作,通过指纹截断与双哈希定位实现多字符集高效过滤。指纹截断需采用fnv64a或xxhash快速哈希并取低8位,桶索引使用独立双哈希避免假阳性。并发安全需以固定数组配合sync atomic实现。
Java使用Poi-tl按Word模板生成动态表格
Poi-tl是Word导出工具,文档周全,支持多级合并表头生成。通过{{text}}、{{?var}}、{{ table}}标签处理模板,传入TableRenderData对象即可动态渲染表格。示例展示用户信息表格生成,并提供工具类消除表格首行缩进,确保格式正确。
Go语言微服务集成Swagger生成交互式API文档完整教程
在Go微服务中集成Swagger常见四大问题:swaginit初始化失败需确保存在packagemain及注释;SwaggerUI加载失败因路由映射错误或未导入docs;@Param注解必须严格遵循格式;部署后接口文档显示localhost因硬编码host,应删除或通过环境变量动态注入。
- 热门数据榜
相关攻略
2026-07-11 06:47
2026-07-11 06:47
2026-07-11 06:47
2026-07-11 06:47
2026-07-11 06:46
2026-07-11 06:46
2026-07-11 06:46
2026-07-11 06:46
热门教程
- 游戏攻略
- 安卓教程
- 苹果教程
- 电脑教程

