您的位置:首页 > 其它

POI解析合并单元格

2016-06-13 22:47 176 查看
excel中的合并单元格其实就是首单元格,只不过该单元格增加了 rowspan和colspan两个属性。
并且把该单元格的高度和宽度变成(例如rowspan=2,colspan=3)2行,3列的的标尺长度,再把被合并的单元格(除了首单元格的其余5个单元格)隐藏。



public class ExcelUtils{


private void readExcel(Workbook wb) {
Sheet sheet = wb.getSheetAt(0);
Row row = null;

for(int i=0; i<sheet.getPhysicalNumberOfRows(); i++)
{
row = sheet.getRow(i);
for(int j = 0; j < row.getLastCellNum();j++)
{
Cell c = row.getCell(j);
boolean isMerge = isMergedRegion(sheet, i, c.getColumnIndex());
//判断是否具有合并单元格
if(isMerge) {
String rs = getMergedRegionValue(sheet, row.getRowNum(), c.getColumnIndex());
System.out.print(rs+" ");
}else {
System.out.print(c.getRichStringCellValue()+" ");
}
}

}

}

/**
* 获取合并单元格的值
* @param sheet
* @param row
* @param column
* @return
*/
public String getMergedRegionValue(Sheet sheet ,int row , int column){
int sheetMergeCount = sheet.getNumMergedRegions(); //获得该sheet所有合并单元格数量

for(int i = 0 ; i < sheetMergeCount ; i++){
CellRangeAddress ca = sheet.getMergedRegion(i); // 获得合并区域
int firstColumn = ca.getFirstColumn();
int lastColumn = ca.getLastColumn();
int firstRow = ca.getFirstRow();
int lastRow = ca.getLastRow();


//判断传入的单元格的行号列号是否在合并单元格的范围内,如果在合并单元格的范围内,择返回合并区域的首单元格格值
if(row >= firstRow && row <= lastRow){

if(column >= firstColumn && column <= lastColumn){
Row fRow = sheet.getRow(firstRow);
Cell fCell = fRow.getCell(firstColumn);
return getCellValue(fCell) ;
}
}
}
//如果该单元格行号列号不在任何一个合并区域,择返回null
return null ;
}

/**
* 判断合并了行
* @param sheet
* @param row
* @param column
* @return
*/
private boolean isMergedRow(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;
}

/**
* 判断指定的单元格是否是合并单元格
* @param sheet
* @param row 行下标
* @param column 列下标
* @return
*/
private 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;
}

/**
* 判断sheet页中是否含有合并单元格
* @param sheet
* @return
*/
private boolean hasMerged(Sheet sheet) {
return sheet.getNumMergedRegions() > 0 ? true : false;
}

/**
* 合并单元格
* @param sheet
* @param firstRow 开始行
* @param lastRow 结束行
* @param firstCol 开始列
* @param lastCol 结束列
*/
private void mergeRegion(Sheet sheet, int firstRow, int lastRow, int firstCol, int lastCol) {
sheet.addMergedRegion(new CellRangeAddress(firstRow, lastRow, firstCol, lastCol));
}

/**
* 获取单元格的值
* @param cell
* @return
*/
public String getCellValue(Cell cell){

if(cell == null) return "";

if(cell.getCellType() == Cell.CELL_TYPE_STRING){

return cell.getStringCellValue();

}else if(cell.getCellType() == Cell.CELL_TYPE_BOOLEAN){

return String.valueOf(cell.getBooleanCellValue());

}else if(cell.getCellType() == Cell.CELL_TYPE_FORMULA){

return cell.getCellFormula() ;

}else if(cell.getCellType() == Cell.CELL_TYPE_NUMERIC){

return String.valueOf(cell.getNumericCellValue());

}
return "";
}
}

}


原理:
通过sheet.getNumMergedRegions();获得所有合并单元格的数量,并且一一遍历,判断传入的单元格行下标和列下标是否在该合并单元格的范围内,如果在,则直接返回该合并区域首单元格的值,如果不在则继续判断下一个合并区域。如果不在任何一个合并区域内,则是非合并单元格
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: