基于POI的读写Excel文件的工具类
依赖的jar包:
import java.io.FileNotFoundException; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.lang.reflect.Field; import java.util.ArrayList; import java.util.Arrays; import java.util.List; import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.ss.usermodel.Cell; import org.apache.poi.ss.usermodel.CellType; 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.ss.usermodel.WorkbookFactory; /** * * 基于POI的读写Excel文件的工具类 * @author 大别山人 * @2018年5月13日 下午4:00:11 */ public final class ExcelUtils { private static <T>Field[] getFields(Class<T> clazz,String[] fieldNames) { Field[] fs = new Field[fieldNames.length]; Field[] fields = clazz.getDeclaredFields(); for (int i = 0; i < fieldNames.length; i++) { O:for (Field field : fields) { field.setAccessible(true); if(field.getName().equals(fieldNames[i])) { fs[i] = field; break O; } } } System.out.println(Arrays.toString(fs)); return fs; } private static <T>String[][] getDatas(String[] titles,List<T> beans,String[] fieldNames) throws Exception{ List<String[]> datas = new ArrayList<>(); if(titles != null && titles.length > 0) { datas.add(titles); } //根据List集合中的JavaBean对象的类型,和参数fieldNames,获取要写出的字段数组; Field[] fs = getFields(beans.get(0).getClass(),fieldNames); for (T t : beans) { String[] data = new String[fs.length]; for (int i = 0; i < fs.length; i++) { if(fs[i] != null) { Object obj = fs[i].get(t); String value = obj == null ? "" : obj.toString(); data[i] = value; } } datas.add(data); } return datas.toArray(new String[datas.size()][]); } /** * 将指定的二维字符串数组中的数据,写出到指定的Excel文件中 * @param datas:保存了要写出的数据的二维数组; * @param output:关联到要输出的Excel文件的输出流 * @throws IOException * @throws FileNotFoundException */ public static void writeToExcel(String[][] datas, OutputStream output) throws IOException, FileNotFoundException { // 创建一个Workbook对象; Workbook book = new HSSFWorkbook(); // 通过workbook对象,创建一个工作表(sheet对象) Sheet sheet = book.createSheet(); for (int i = 0; i < datas.length; i++) { // 通过工作表创建行 Row row = sheet.createRow(i); for (int j = 0; j < datas[i].length; j++) { // 通过行创建单元格 Cell cell = row.createCell(j); cell.setCellType(CellType.STRING); // 为单元格设置内容 cell.setCellValue(datas[i][j]); } } book.write(output); book.close(); } /** * 将指定集合中的所有JavaBean数据,写出到关联指定Excel文件的输出流中; * @param titles:输出的Excel文件的标题行的内容 * @param fieldNames:一行中的各个列对应的JavaBean中的字段 * @param beans:要输出的所有JavaBean对象 * @param output:关联到指定Excel文件的输出流 * @throws Exception */ public static <T>void writeToExcel(String[] titles,String[] fieldNames,List<T> beans,OutputStream output) throws Exception { String[][] datas = getDatas(titles, beans, fieldNames); writeToExcel(datas, output); } /** * 从指定的Excel的输入流中读取数据,写到指定类型的bean对象的List集合中; * @param input:关联到某个Excel文件的输入流 * @param clazz:要封装一行数据的JavaBean的类型 * @param fieldNames:一行数据中的列按顺序和JavaBean中对应的字段 * @return * @throws Exception */ public static <T> List<T> readExcel(InputStream input, Class<T> clazz,String[] fieldNames) throws Exception { List<T> list = new ArrayList<>(); Field[] fs = getFields(clazz,fieldNames); // 创建一个Workbook对象 Workbook book = WorkbookFactory.create(input); // 通过Workbook对象,获取里面的工作表(sheet对象) Sheet sheet = book.getSheetAt(0); // 获取工作表中的行 for (int i = 1; i <= sheet.getLastRowNum(); i++) { // 通过行号获取行 Row row = sheet.getRow(i); T t = clazz.newInstance(); // 遍历获取一行中的所有单元格 for (int j = 0; j < fs.length; j++) { if(fs[j] != null) { Cell cell = row.getCell(j); cell.setCellType(CellType.STRING); setCellValue(fs[j],t,cell); } } list.add(t); } return list; } private static void setCellValue(Field field,Object bean,Cell cell) throws Exception { String str = cell.toString(); Class clazz = field.getType(); if(clazz == byte.class) { field.set(bean, Byte.parseByte(str)); }else if(clazz == short.class) { field.set(bean, Short.parseShort(str)); }else if(clazz == int.class) { field.set(bean, Integer.parseInt(str)); }else if(clazz == long.class) { field.set(bean, Long.parseLong(str)); }else if(clazz == double.class) { field.set(bean, Double.parseDouble(str)); }else if(clazz == float.class) { field.set(bean, Float.parseFloat(str)); }else if(clazz == boolean.class) { field.set(bean, Boolean.parseBoolean(str)); }else { field.set(bean, str); } } }