POI上传Excel解析存入数据库


poi getCellType类型说明
CellType 类型 值
CELL_TYPE_NUMERIC 数值型 0
CELL_TYPE_STRING 字符串型 1
CELL_TYPE_FORMULA 公式型 2
CELL_TYPE_BLANK 空值 3
CELL_TYPE_BOOLEAN 布尔型 4
CELL_TYPE_ERROR 错误 5

excel文件后缀
.xls  2003版
XLSX  2007版

excel采用HTTP协议传输的。

Spring MVC中上传文件,将文件转换为输入流
MultipartHttpServletRequest multipartRequest =(MultipartHttpServletRequest) req;
//SpringMVC上传文件的控件
//提取;文件,这个参数必须和上传控件的name一致。返回上传内容对象,如果不存在就返回null.
MultipartFile multipartFile = multipartRequest.getFile("file");
InputStream in = multipartFile.getInputStream();//获取控件内容的输入流

将得到的文件输入流,解析为一个字符串中
//针对2003版本
//创建excel2003的文件文本抽取对象
Workbook wb = new HSSFWorkbook(new POIFSFileSystem(in));
//声明相关的excel抽取对象
ExcelExtractor extractor = new ExcelExtractor((HSSFWorkbook) wb);
String a = extractor.getText();//保存了excel文件中多有的内容字符串

//针对2007版本
//创建excel2007的文件文本抽取对象
Workbook wb = new XSSFWorkbook(in);
//声明相关的excel抽取对象
XSSFExcelExtractor extractor =  new XSSFExcelExtractor((XSSFWorkbook) wb);
String a = extractor.getText();





----------------------------------------------------------------
POI读写2007+的excel时
Exception in thread "main" org.apache.poi.POIXMLException: java.lang.reflect.InvocationTargetException

at org.apache.poi.xssf.usermodel.XSSFFactory.createDocumentPart(XSSFFactory.java:62)

错误原因:
xbean的jar包有冲突,删除xbean的包引用POI里的xmlbeans-2.3.0,可正确读取

我也遇到了同样的问题.
如果操作xls文件的时候没有问题, 当操作xlsx文件的时候就会报这个错.

我的问题已经解决了.
原因: 主要是因为xls和xlsx的解析方式不一样, 导致使用的类不同.
xls返回的是HSSFWorkbook   , 而xlsx返回的是XSSFWorkbook.
我自己试验了一种方法是:
HSSFWorkbook book;
try {
     book = new HSSFWorkbook(in);
} catch (Exception ex) {
     book = new XSSFWorkbook(in);
}
其结果不尽人意, 而且报错莫名其妙.(反正我是没搞懂).

进入正题: 以下方法是正解,
1. 新建个方法, 返回HSSFWorkbook和XSSFWorkbook所实现的接口
文件的前8个字节,然后根据这个判断
用读取文件头的方法,07有规律,文件头是"PK";但是03的话 一直不知道~
public Workbook create(InputStream inp) throws IOException, InvalidFormatException {
if (!inp.markSupported()) {
inp = new PushbackInputStream(inp, ;
}
if (POIFSFileSystem.hasPOIFSHeader(inp)) {
log.error("2003及以下");
return new HSSFWorkbook(inp);
}
if (POIXMLDocument.hasOOXMLHeader(inp)) {
log.error("2007及以上");
return new XSSFWorkbook(OPCPackage.open(inp));
}
log.error("你的excel版本目前poi解析不了");
return null;
}

2.在new Workbook对象的时候直接调用该静态方法去构造.
Workbook book = create(in);
3. 切记, 如果workbook使用了接口的话, 那么Sheet也一定要用接口, 不要用实现类了.
Sheet sheet = book.getSheetAt(0);


/*
 * @(#)demo02
 * @(#)demo.java	2014-7-3
 * 
 * Copyright © 2001-2010, All rights reserved.
 * iSoftStone Information Technology ( Group ) Co., Ltd.
 */
package demo02;

/**
 * <P>Description: TODO</P>
 * @ClassName: demo
 * @author zhangmeijia  2014-7-3 下午02:50:54
 * @see TODO
 */
public class demo {
	
	 //<p>Description: 解析Excel文件</p>
	public List<User> readExcel(final String fileName, HttpServletRequest req) throws Exception {
		List<User> UserList = null;
		MultipartHttpServletRequest multipartRequest = (MultipartHttpServletRequest) req;
		MultipartFile multipartFile = multipartRequest.getFile("file");
		InputStream in = multipartFile.getInputStream();
		Workbook wb = null;//声明工作薄
		wb = create(in);
		//		String hz = fileName.substring(fileName.lastIndexOf('.'), fileName.length()).toUpperCase();
		//		if (".XLS".equals(hz)) {
		//			wb = new HSSFWorkbook(new POIFSFileSystem(in));
		//		} else {
		//			wb = new XSSFWorkbook(in);
		//		}
		//解析Excel文件内容,将其封装为实体集合,返回集合

		UserList = analysis(wb);
		return UserList;
	}

	public Workbook create(InputStream inp) throws Exception {
		if (!inp.markSupported()) {
			inp = new PushbackInputStream(inp, 8);
		}
		if (POIFSFileSystem.hasPOIFSHeader(inp)) {
			log.error("2003及以下");
			return new HSSFWorkbook(inp);
		}
		if (POIXMLDocument.hasOOXMLHeader(inp)) {
			log.error("2007及以上");
			return new XSSFWorkbook(OPCPackage.open(inp));
		}
		log.error("你的excel版本目前poi解析不了");
		return null;
	}

	 * <p>Description: 解析。遍历所有数据</p>
	public List<User> analysis(Workbook wb) throws Exception {
		List<User> UserList = new ArrayList<User>();
		try {
			for (int k = 0; k < wb.getNumberOfSheets(); k++) {// 遍历每一个Sheet
				Sheet sheet = wb.getSheetAt(k);
				int rows = sheet.getPhysicalNumberOfRows();
				List<String> list = new ArrayList<String>();
				for (int r = 0; r < rows; r++) {//遍历每一行
					if (r == 0) {
						continue;
					}
					Row row = sheet.getRow(r);
					if (row == null) {
						continue;
					}
					int cells = row.getPhysicalNumberOfCells() + 1;// 每一行单元格数目
					//1.解析一行数据为一个字符串
					String str = analysisOneLineTdList(cells, row);
					list.add(str);
				}
				//2.将数据字符串的集合,生成实体对象放入集合,并返回
				List<User> cusInfoList = getUserList(list);
				for (User c : cusInfoList) {
					UserList.add(c);
				}
			}
		} catch (Exception e) {
			log.error("Excel文件导入,analysis方法失败");
			e.printStackTrace();
			throw new Exception();
		}
		return UserList;
	}

	 * <p>Description: 解析每一行</p>
	public String analysisOneLineTdList(int cells, Row row) throws Exception {
		String lineStr = "";
		String str = "";
		try {
			for (short c = 0; c < cells; c++) {
				Cell cell = row.getCell(c);
				if (cell == null) {
					str = "";
				} else {
					switch (cell.getCellType()) {// 单元格的类型
					case Cell.CELL_TYPE_FORMULA:// 公式型
						str = cell.getNumericCellValue() + "";
						break;
					case Cell.CELL_TYPE_NUMERIC:// 数值型
						if (DateUtil.isCellDateFormatted(cell)) {
							Date date = cell.getDateCellValue();
							SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
							str = sdf.format(date).toString();
						} else {
							BigDecimal num = new BigDecimal(cell.getNumericCellValue());
							str = String.valueOf(num);
						}
						break;
					case Cell.CELL_TYPE_STRING:// 字符串型
						str = cell.getRichStringCellValue().toString().replaceAll("'", "''");
						break;
					case Cell.CELL_TYPE_BOOLEAN:// 布尔型
						str = cell.getBooleanCellValue() + "";
						break;
					case Cell.CELL_TYPE_BLANK:// 空值
						str = "";
						break;
					case Cell.CELL_TYPE_ERROR:// 错误
						str = "";
						break;
					default:
						str = "";
					}
				}
				lineStr = lineStr + "  ,  " + str;
			}
		} catch (Exception e) {
			log.error("Excel文件导入,解析一行analysisOneLineTdList方法失败");
			e.printStackTrace();
			throw new Exception();
		}
		lineStr = lineStr.replaceFirst("  ,  ", "");
		return lineStr;// 以字符串返回该行的数据
	}

	 * <p>Description: 获取封装实体的集合</p>
	public List<User> getUserList(List<String> list) throws Exception {
		List<User> UserList = new ArrayList<User>();
		for (int r = 0; r < list.size(); r++) {
			String rowsStr = list.get(r);
			String[] td = rowsStr.split("  ,  ");
			//数据限制

			User ci = new User();
			ci.setSerialNumber(td[0].trim());
			ci.setOrderNo(td[1].trim());
			ci.setProductCode(td[2].trim());
			ci.setProductName(td[3].trim());
			ci.setCustomerName(td[4].trim());
			.....ci..
			} catch (ParseException e) {
				log.error("Excel文件导入,解析日期getUserList方法失败");
				e.printStackTrace();
				throw new Exception();
			}
			UserList.add(ci);
		}
		return UserList;
	}

}

你可能感兴趣的:(java,Excel)