您好,登錄后才能下訂單哦!
使用apache poi怎么實(shí)現(xiàn)導(dǎo)出excel文件?相信很多沒有經(jīng)驗(yàn)的人對(duì)此束手無策,為此本文總結(jié)了問題出現(xiàn)的原因和解決方法,通過這篇文章希望你能解決這個(gè)問題。
代碼如下:
package com.icourt.util; import org.apache.commons.collections4.CollectionUtils; import org.apache.poi.openxml4j.exceptions.InvalidFormatException; import org.apache.poi.ss.usermodel.*; import org.apache.poi.ss.util.CellRangeAddress; import java.io.*; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.Map.Entry; import java.util.regex.Matcher; import java.util.regex.Pattern; /** * 描述:poi根據(jù)模板導(dǎo)出excel,根據(jù)excel坐標(biāo)賦值,如(B1) */ public class ExcelExportUtil { //模板map private Map<String, Workbook> tempWorkbook = new HashMap<String, Workbook>(); //模板輸入流map private Map<String, InputStream> tempStream = new HashMap<String, InputStream>(); /** * 功能:按模板向Excel中相應(yīng)地方填充數(shù)據(jù) */ public void writeData(String templateFilePath, Map<String, Object> dataMap, int sheetNo) throws IOException, InvalidFormatException { if (dataMap == null || dataMap.isEmpty()) { return; } //讀取模板 Workbook wbModule = getTempWorkbook(templateFilePath); //數(shù)據(jù)填充的sheet Sheet wsheet = wbModule.getSheetAt(sheetNo); for (Entry<String, Object> entry : dataMap.entrySet()) { String point = entry.getKey(); Object data = entry.getValue(); TempCell cell = getCell(point, data, wsheet); //指定坐標(biāo)賦值 setCell(cell, wsheet); } //設(shè)置生成excel中公式自動(dòng)計(jì)算 wsheet.setForceFormulaRecalculation(true); } /** * 功能:按模板向Excel中列表填充數(shù)據(jù).只支持列合并 */ public void writeDateList(String templateFilePath, String[] heads, List<Map<Integer, Object>> datalist, int sheetNo) throws IOException, InvalidFormatException { if (heads == null || heads.length <= 0 || CollectionUtils.isEmpty(datalist)) { return; } //讀取模板 Workbook wbModule = getTempWorkbook(templateFilePath); //數(shù)據(jù)填充的sheet Sheet wsheet = wbModule.getSheetAt(sheetNo); //列表數(shù)據(jù)模板cell List<TempCell> tempCells = new ArrayList<TempCell>(heads.length); for (String point : heads) { TempCell tempCell = getCell(point, null, wsheet); //取得合并單元格位置 -1:表示不是合并單元格 int pos = isMergedRegion(wsheet, tempCell.getRow(), tempCell.getColumn()); if (pos > -1) { CellRangeAddress range = wsheet.getMergedRegion(pos); tempCell.setColumnSize(range.getLastColumn() - range.getFirstColumn()); } tempCells.add(tempCell); } //賦值 for (int i = 0; i < datalist.size(); i++) {//數(shù)據(jù)行 Map<Integer, Object> dataMap = datalist.get(i); for (int j = 0; j < tempCells.size(); j++) {//列 TempCell tempCell = tempCells.get(j); tempCell.setData(dataMap.get(j + 1)); setCell(tempCell, wsheet); tempCell.setRow(tempCell.getRow() + 1); } } } /** * 功能:獲取輸入工作區(qū) */ private Workbook getTempWorkbook(String templateFilePath) throws IOException, InvalidFormatException { if (!tempWorkbook.containsKey(templateFilePath)) { InputStream inputStream = getInputStream(templateFilePath); tempWorkbook.put(templateFilePath, WorkbookFactory.create(inputStream)); } return tempWorkbook.get(templateFilePath); } /** * 功能:獲得模板輸入流 */ private InputStream getInputStream(String templateFilePath) throws FileNotFoundException { if (!tempStream.containsKey(templateFilePath)) { tempStream.put(templateFilePath, new FileInputStream((templateFilePath))); } return tempStream.get(templateFilePath); } /** * 功能:獲取單元格數(shù)據(jù),樣式(根據(jù)坐標(biāo):B3) */ private TempCell getCell(String point, Object data, Sheet sheet) { TempCell tempCell = new TempCell(); //得到列 字母 String lineStr = ""; String reg = "[A-Z]+"; Pattern p = Pattern.compile(reg); Matcher m = p.matcher(point); while (m.find()) { lineStr = m.group(); } //將列字母轉(zhuǎn)成列號(hào) 根據(jù)ascii轉(zhuǎn)換 char[] ch = lineStr.toCharArray(); int column = 0; for (int i = 0; i < ch.length; i++) { char c = ch[i]; int post = ch.length - i - 1; int r = (int) Math.pow(10, post); column = column + r * ((int) c - 65); } tempCell.setColumn(column); //得到行號(hào) reg = "[1-9]+"; p = Pattern.compile(reg); m = p.matcher(point); while (m.find()) { tempCell.setRow((Integer.parseInt(m.group()) - 1)); } //獲取模板指定單元格樣式,設(shè)置到tempCell(寫列表數(shù)據(jù)的時(shí)候用) Row rowIn = sheet.getRow(tempCell.getRow()); if (rowIn == null) { rowIn = sheet.createRow(tempCell.getRow()); } Cell cellIn = rowIn.getCell(tempCell.getColumn()); if (cellIn == null) { cellIn = rowIn.createCell(tempCell.getColumn()); } tempCell.setCellStyle(cellIn.getCellStyle()); tempCell.setData(data); return tempCell; } /** * 功能:給指定坐標(biāo)單元格賦值 */ private void setCell(TempCell tempCell, Sheet sheet) { if (tempCell.getColumnSize() > -1) { CellRangeAddress rangeAddress = mergeRegion(sheet, tempCell.getRow(), tempCell.getRow(), tempCell.getColumn(), tempCell.getColumn() + tempCell.getColumnSize()); setRegionStyle(tempCell.getCellStyle(), rangeAddress, sheet); } Row rowIn = sheet.getRow(tempCell.getRow()); if (rowIn == null) { copyRows(tempCell.getRow() - 1, tempCell.getRow() - 1, tempCell.getRow(), sheet);//復(fù)制上一行 rowIn = sheet.getRow(tempCell.getRow()); } Cell cellIn = rowIn.getCell(tempCell.getColumn()); if (cellIn == null) { cellIn = rowIn.createCell(tempCell.getColumn()); } //根據(jù)data類型給cell賦值 if (tempCell.getData() instanceof String) { cellIn.setCellValue((String) tempCell.getData()); } else if (tempCell.getData() instanceof Integer) { cellIn.setCellValue((int) tempCell.getData()); } else if (tempCell.getData() instanceof Double) { cellIn.setCellValue((double) tempCell.getData()); } else { cellIn.setCellValue((String) tempCell.getData()); } //樣式 if (tempCell.getCellStyle() != null && tempCell.getColumnSize() == -1) { cellIn.setCellStyle(tempCell.getCellStyle()); } } /** * 功能:寫到輸出流并移除資源 */ public void writeAndClose(String templateFilePath, OutputStream os) throws IOException, InvalidFormatException { if (getTempWorkbook(templateFilePath) != null) { getTempWorkbook(templateFilePath).write(os); tempWorkbook.remove(templateFilePath); } if (getInputStream(templateFilePath) != null) { getInputStream(templateFilePath).close(); tempStream.remove(templateFilePath); } } /** * 功能:判斷指定的單元格是否是合并單元格 */ private Integer isMergedRegion(Sheet sheet, int row, int column) { for (int i = 0; i < sheet.getNumMergedRegions(); 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 i; } } } return -1; } /** * 功能:合并單元格 */ private CellRangeAddress mergeRegion(Sheet sheet, int firstRow, int lastRow, int firstCol, int lastCol) { CellRangeAddress rang = new CellRangeAddress(firstRow, lastRow, firstCol, lastCol); sheet.addMergedRegion(rang); return rang; } /** * 功能:設(shè)置合并單元格樣式 */ private void setRegionStyle(CellStyle cs, CellRangeAddress region, Sheet sheet) { for (int i = region.getFirstRow(); i <= region.getLastRow(); i++) { Row row = sheet.getRow(i); if (row == null) row = sheet.createRow(i); for (int j = region.getFirstColumn(); j <= region.getLastColumn(); j++) { Cell cell = row.getCell(j); if (cell == null) { cell = row.createCell(j); cell.setCellValue(""); } cell.setCellStyle(cs); } } } /** * 功能:copy rows */ private void copyRows(int startRow, int endRow, int pPosition, Sheet sheet) { int pStartRow = startRow - 1; int pEndRow = endRow - 1; int targetRowFrom; int targetRowTo; int columnCount; CellRangeAddress region = null; int i; int j; if (pStartRow == -1 || pEndRow == -1) { return; } // 拷貝合并的單元格 for (i = 0; i < sheet.getNumMergedRegions(); i++) { region = sheet.getMergedRegion(i); if ((region.getFirstRow() >= pStartRow) && (region.getLastRow() <= pEndRow)) { targetRowFrom = region.getFirstRow() - pStartRow + pPosition; targetRowTo = region.getLastRow() - pStartRow + pPosition; CellRangeAddress newRegion = region.copy(); newRegion.setFirstRow(targetRowFrom); newRegion.setFirstColumn(region.getFirstColumn()); newRegion.setLastRow(targetRowTo); newRegion.setLastColumn(region.getLastColumn()); sheet.addMergedRegion(newRegion); } } // 設(shè)置列寬 for (i = pStartRow; i <= pEndRow; i++) { Row sourceRow = sheet.getRow(i); columnCount = sourceRow.getLastCellNum(); if (sourceRow != null) { Row newRow = sheet.createRow(pPosition - pStartRow + i); newRow.setHeight(sourceRow.getHeight()); for (j = 0; j < columnCount; j++) { Cell templateCell = sourceRow.getCell(j); if (templateCell != null) { Cell newCell = newRow.createCell(j); copyCell(templateCell, newCell); } } } } } /** * 功能:copy cell,不copy值 */ private void copyCell(Cell srcCell, Cell distCell) { distCell.setCellStyle(srcCell.getCellStyle()); if (srcCell.getCellComment() != null) { distCell.setCellComment(srcCell.getCellComment()); } int srcCellType = srcCell.getCellType(); distCell.setCellType(srcCellType); } /** * 描述:臨時(shí)單元格數(shù)據(jù) */ class TempCell { private int row; private int column; private CellStyle cellStyle; private Object data; //用于列表合并,表示幾列合并 private int columnSize = -1; public int getColumn() { return column; } public void setColumn(int column) { this.column = column; } public int getRow() { return row; } public void setRow(int row) { this.row = row; } public CellStyle getCellStyle() { return cellStyle; } public void setCellStyle(CellStyle cellStyle) { this.cellStyle = cellStyle; } public Object getData() { return data; } public void setData(Object data) { this.data = data; } public int getColumnSize() { return columnSize; } public void setColumnSize(int columnSize) { this.columnSize = columnSize; } } public static void main(String[] args) throws FileNotFoundException, IOException, InvalidFormatException { String templateFilePath = ExcelExportUtil.class.getClassLoader().getResource("plugin/ProTiming.xlsx").getPath(); File file = new File("/Users/sql/Downloads/test/data.xlsx"); OutputStream os = new FileOutputStream(file); ExcelExportUtil excel = new ExcelExportUtil(); Map<String, Object> dataMap = new HashMap<String, Object>(); dataMap.put("B1", "03_Alpha_項(xiàng)目工作時(shí)間統(tǒng)計(jì)表"); dataMap.put("B2", "統(tǒng)計(jì)時(shí)間:2017/01/01 - 2017/03/31"); excel.writeData(templateFilePath, dataMap, 0); List<Map<Integer, Object>> datalist = new ArrayList<Map<Integer, Object>>(); Map<Integer, Object> data = new HashMap<Integer, Object>(); data.put(1, "3/10/17"); data.put(2, "18:50"); data.put(3, "19:00"); data.put(4, "李子鵬"); data.put(5, "新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用"); data.put(6, "代碼開發(fā)"); data.put(7, "3.17"); datalist.add(data); data = new HashMap<Integer, Object>(); data.put(1, "3/10/17"); data.put(2, "18:50"); data.put(3, "19:00"); data.put(4, "李子鵬"); data.put(5, "新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用"); data.put(6, "代碼開發(fā)"); data.put(7, "3.17"); datalist.add(data); data = new HashMap<Integer, Object>(); data.put(1, "3/10/17"); data.put(2, "18:50"); data.put(3, "19:00"); data.put(4, "李子鵬"); data.put(5, "新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用"); data.put(6, "代碼開發(fā)"); data.put(7, "3.17"); datalist.add(data); data = new HashMap<Integer, Object>(); data.put(1, "3/10/17"); data.put(2, "18:50"); data.put(3, "19:00"); data.put(4, "李子鵬"); data.put(5, "新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用"); data.put(6, "代碼開發(fā)"); data.put(7, "3.17"); datalist.add(data); data = new HashMap<Integer, Object>(); data.put(1, "3/10/17"); data.put(2, "18:50"); data.put(3, "19:00"); data.put(4, "李子鵬"); data.put(5, "新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用"); data.put(6, "代碼開發(fā)"); data.put(7, "3.17"); datalist.add(data); data = new HashMap<Integer, Object>(); data.put(1, "3/10/17"); data.put(2, "18:50"); data.put(3, "19:00"); data.put(4, "李子鵬"); data.put(5, "新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用"); data.put(6, "代碼開發(fā)"); data.put(7, "3.17"); datalist.add(data); data = new HashMap<Integer, Object>(); data.put(1, "3/10/17"); data.put(2, "18:50"); data.put(3, "19:00"); data.put(4, "李子鵬"); data.put(5, "新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用"); data.put(6, "代碼開發(fā)"); data.put(7, "3.17"); datalist.add(data); data = new HashMap<Integer, Object>(); data.put(1, "3/10/17"); data.put(2, "18:50"); data.put(3, "19:00"); data.put(4, "李子鵬"); data.put(5, "新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用"); data.put(6, "代碼開發(fā)"); data.put(7, "3.17"); datalist.add(data); data = new HashMap<Integer, Object>(); data.put(1, "3/10/17"); data.put(2, "18:50"); data.put(3, "19:00"); data.put(4, "李子鵬"); data.put(5, "新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用新增項(xiàng)目鍵值對(duì)接口,供任務(wù)計(jì)時(shí)調(diào)用"); data.put(6, "代碼開發(fā)"); data.put(7, "3.17"); datalist.add(data); data = new HashMap<Integer, Object>(); data.put(1, ""); data.put(2, ""); data.put(3, ""); data.put(4, ""); data.put(5, ""); data.put(6, ""); data.put(7, ""); datalist.add(data); String[] heads = new String[]{"B4", "C4", "D4", "E4", "F4", "G4", "H4"}; excel.writeDateList(templateFilePath, heads, datalist, 0); //寫到輸出流并移除資源 excel.writeAndClose(templateFilePath, os); os.flush(); os.close(); } }
大體思路:
最主要是制作好模版
代碼根據(jù)模版,讀取設(shè)置好的列的格式,在循環(huán)數(shù)據(jù)行,讀取模版中的對(duì)應(yīng)的行,存在該行就取得,不存在看是否需要copy某一行,不需要就手動(dòng)創(chuàng)建無制定格式的行,后面在為該行的每一列對(duì)應(yīng)的給個(gè)單元格制定格式和數(shù)據(jù)。
看完上述內(nèi)容,你們掌握使用apache poi怎么實(shí)現(xiàn)導(dǎo)出excel文件的方法了嗎?如果還想學(xué)到更多技能或想了解更多相關(guān)內(nèi)容,歡迎關(guān)注億速云行業(yè)資訊頻道,感謝各位的閱讀!
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。