java使用poi读取excel表格

前言

用户上传excel表格,后端读取excel中的数据并存入数据库。

这里只演示如何读取到excel表格中的内容,excel中包括图片、日期、字符串格式。

导入依赖

        <dependency>
            <groupId>org.apache.poi</groupId>
            <artifactId>poi</artifactId>
            <version>3.17</version>
        </dependency>
        <dependency>
            <groupId>org.apache.poi</groupId>
            <artifactId>poi-ooxml</artifactId>
            <version>3.17</version>
        </dependency>
        <dependency>
            <groupId>commons-io</groupId>
            <artifactId>commons-io</artifactId>
            <version>2.6</version>
        </dependency>
        <dependency>
            <groupId>commons-fileupload</groupId>
            <artifactId>commons-fileupload</artifactId>
            <version>1.3.3</version>
        </dependency>

excel表格样式

 

 实体类

public class User {
    private Integer id;
    private String name;
    private Integer age;
    private String sex;
    private String picPath;
    private String date;
    private String department;


    public User() {
    }

读取表格工具类

import com.csv.pojo.User;
import org.apache.poi.POIXMLDocumentPart;
import org.apache.poi.hssf.usermodel.*;
import org.apache.poi.ss.usermodel.PictureData;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.*;
import org.openxmlformats.schemas.drawingml.x2006.spreadsheetDrawing.CTMarker;

import java.io.*;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * Excel工具类
 */
public class ExcelUtil {

    /**
     * 判断文件是否存在
     *
     * @param fileName
     * @return
     */
    public static boolean fileExist(String fileName) {
        boolean flag = false;
        File file = new File(fileName);
        flag = file.exists();
        return flag;
    }

    /**
     * 新文件写入数据
     *
     * @return
     */
    public static List<User> writeNewFile() {
        List<User> userList = new ArrayList<>();
        User user;
        for (int i = 0; i < 10; i++) {
            user = new User();
            user.setName("u" + i);
            user.setAge(i);
            user.setSex("男");
            userList.add(user);
        }
        return userList;
    }

    /**
     * 从excel中读取数据
     *
     * @param xls         true xls文件,false xlsx文件
     * @param inputStream 文件输入流
     * @return 数据封装到对象
     */
    public static List<User> getDataFromExcel(boolean xls, InputStream inputStream) {
        SimpleDateFormat sf = new SimpleDateFormat("yyyy-MM-dd");
        Workbook workbook = null;
        List<User> userList = new ArrayList<>();
        try {
            if (xls) {
                workbook = new HSSFWorkbook(inputStream);
            } else {
                workbook = new XSSFWorkbook(inputStream);
            }

            // 得到一个工作表
            Sheet sheet = workbook.getSheetAt(0);
            // 得到表头
            Row rowHead = sheet.getRow(0);
            // 判断表头是否正确
            if (rowHead.getPhysicalNumberOfCells() < 1) {
                throw new Exception("表头错误");
            }

            // 获取照片
            Map<String, PictureData> pictures;
            if (xls) {
                pictures = getPictures((HSSFSheet) sheet);
            } else {
                pictures = getPictures((XSSFSheet) sheet);
            }

            // 获取数据
            for (int i = 2; i <= sheet.getLastRowNum(); i++) {
                // 获取第i行
                Row row = sheet.getRow(i);
                // 获取第i行各个列的数据
                Integer id = (int) row.getCell(0).getNumericCellValue();
                String username = row.getCell(1).getStringCellValue();
                Integer age = (int) row.getCell(2).getNumericCellValue();
                String sex = row.getCell(3).getStringCellValue();
                String savePath = savePicture(id, pictures.get(i + "-4"));
                String date;
                // 判断该单元格的数据类型
                switch (row.getCell(5).getCellTypeEnum()) {
                    case STRING: // 字符串类型
                        date = row.getCell(5).getStringCellValue();
                        break;
                    case NUMERIC: // 日期类型
                        date = sf.format(row.getCell(5).getDateCellValue());
                        break;
                    default:
                        date = "";
                        break;
                }
                String department = "";
                if (isMergedRegion(sheet,i,6)) {
                    department = getMergedRegionValue(sheet,i,6);
                }else {
                    department = row.getCell(6).getStringCellValue();
                }

                userList.add(new User(id, username, age, sex, savePath, date, department));
                
            }

        } catch (Exception e) {
            e.printStackTrace();
        }

        return userList;
    }

    /**
     * xls获取照片
     */
    private static Map<String, PictureData> getPictures(HSSFSheet sheet) {
        Map<String, PictureData> map = new HashMap<>();
        List<HSSFShape> list = sheet.getDrawingPatriarch().getChildren();
        for (HSSFShape shape : list) {
            if (shape instanceof HSSFPicture) {
                HSSFPicture picture = (HSSFPicture) shape;
                HSSFClientAnchor clientAnchor = picture.getClientAnchor();
                HSSFPictureData pictureData = picture.getPictureData();
                String key = clientAnchor.getRow1() + "-" + clientAnchor.getCol1();
                map.put(key, pictureData);
            }
        }
        return map;
    }

    /**
     * xlsx获取照片
     */
    private static Map<String, PictureData> getPictures(XSSFSheet sheet) {
        Map<String, PictureData> map = new HashMap<>();
        List<POIXMLDocumentPart> list = sheet.getRelations();
        for (POIXMLDocumentPart part : list) {
            if (part instanceof XSSFDrawing) {
                XSSFDrawing drawing = (XSSFDrawing) part;
                List<XSSFShape> shapes = drawing.getShapes();
                for (XSSFShape shape : shapes) {
                    XSSFPicture picture = (XSSFPicture) shape;
                    XSSFClientAnchor anchor = picture.getPreferredSize();
                    CTMarker marker = anchor.getFrom();
                    String key = marker.getRow() + "-" + marker.getCol();
                    map.put(key, picture.getPictureData());
                }
            }
        }
        return map;
    }

    /**
     * 照片保存在本地
     */
    private static String savePicture(int id, PictureData picData) throws IOException {
        if (picData != null) {
            byte[] data = picData.getData();
            String fileName = id + "-" + "照片";
            String filePath = "D:\\JavaCode\\testmaven14excel\\image\\";
            FileOutputStream out = new FileOutputStream(filePath + fileName + ".png");
            out.write(data);
            out.close();
            return filePath + fileName + ".png";
        }
        return "";
    }

    /**
     * 获取合并单元格的值
     * @param sheet 表格
     * @param row 行
     * @param column 列
     */
    private static String getMergedRegionValue(Sheet sheet,int row,int column){
        int sheetMergeCount = sheet.getNumMergedRegions();
        for (int i = 0; i < sheetMergeCount; i++){
            CellRangeAddress range = sheet.getMergedRegion(i);
            int firstColumn = range.getFirstColumn();
            int lastColumn = range.getLastColumn();
            int firstRow = range.getFirstRow();
            int lastRow = range.getLastRow();
            if (row>=firstRow&&row<=lastRow) {
                if (column>=firstColumn&&column<=lastColumn) {
                    Row fRow = sheet.getRow(firstRow);
                    Cell fCell = fRow.getCell(firstColumn);
                    return fCell.getStringCellValue();
                }
            }
        }
        return "";
    }

    /**
     * 判断指定的单元格是否是合并单元格
     * @param sheet 表格
     * @param row 行下标
     * @param column 列下标
     */
    private static boolean isMergedRegion(Sheet sheet,int row,int column){
        int sheetMergeCount = sheet.getNumMergedRegions();
        for (int i = 0; i < sheetMergeCount; i++) {
            CellRangeAddress range = sheet.getMergedRegion(i);
            int firstColumn = range.getFirstColumn();
            int lastColumn = range.getLastColumn();
            int firstRow = range.getFirstRow();
            int lastRow = range.getLastRow();
            if (row>=firstRow&&row<=lastRow) {
                if (column>=firstColumn&&column<=lastColumn) {
                    return true;
                }
            }
        }
        return false;
    }
}

控制层接口

@RestController
@RequestMapping("/excel")
@CrossOrigin(maxAge = 3600)
public class ExcelController {


    @RequestMapping(value = "/upload",method = RequestMethod.POST)
    public ResultMessage readFile(@RequestParam(value = "excelFile") MultipartFile excelFile, HttpServletRequest request) throws IOException {
        // 文件名
        String name = excelFile.getOriginalFilename();
        boolean b;
        if (name.endsWith(".xls")) {
            b=true;
        }else if(name.endsWith(".xlsx")){
            b=false;
        }else if(name.endsWith(".jpg")||name.endsWith(".png")){
            System.out.println("收到图片文件"+name);
            return new ResultMessage(true,"这是图片",null);
        }
        else {
            return new ResultMessage(false,"不是excel文件",null);
        }
        List<User> dataFromExcel = ExcelUtil.getDataFromExcel(b,excelFile.getInputStream());
        for (User user : dataFromExcel) {
            System.out.println(user.toString());
        }
        return new ResultMessage(true,"解析文件",dataFromExcel);
    }
}

效果演示

[{
	"id": 1,
	"name": "瑞秋",
	"age": 25,
	"sex": "女",
	"picPath": "D:\\JavaCode\\testmaven14excel\\image\\1-照片.png",
	"date": "2022-02-18",
	"department": "3601"
}, {
	"id": 2,
	"name": "莫妮卡",
	"age": 26,
	"sex": "女",
	"picPath": "D:\\JavaCode\\testmaven14excel\\image\\2-照片.png",
	"date": "2022-02-19",
	"department": "3601"
}, {
	"id": 3,
	"name": "乔伊",
	"age": 24,
	"sex": "男",
	"picPath": "",
	"date": "2022-02-20",
	"department": "3602"
}, {
	"id": 4,
	"name": "钱德勒",
	"age": 26,
	"sex": "男",
	"picPath": "",
	"date": "2022/2/21",
	"department": "3602"
}, {
	"id": 5,
	"name": "罗斯",
	"age": 27,
	"sex": "男",
	"picPath": "",
	"date": "2022/2/22",
	"department": ""
}, {
	"id": 6,
	"name": "菲比",
	"age": 25,
	"sex": "女",
	"picPath": "",
	"date": "2022-02-23",
	"department": ""
}]

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值