一、NPOI简介

NPOI是一个开源项目,可以读/写xls,doc,ppt文件,有着广泛的应用。

使用NPOI能够帮助开发者在没有安装微软Office的情况下读写Office 97-2003的文件,支持的文件格式包括xls, doc, ppt等。NPOI是构建在POI 3.x版本之上的,它可以在没有安装Office的情况下对Word/Excel文档进行读写操作。

 ​

二、安装

Nuget命令


Install-Package NPOI


或者使用Nuget包管理安装

.Net Excel操作之NPOI(一)简介_c#

.Net Excel操作之NPOI(一)简介_数据_02

安装结果:

.Net Excel操作之NPOI(一)简介_封装_03

三、Excel操作示例

1.Excel函数问题:


  • Excel 2003版本,最大行数是65536行。(xls) HSSFWorkbook workbook = new HSSFWorkbook();
  • Excel 2007版本以上,最大行数是1048576行。(xlsx) XSSFWorkbook workbook = new XSSFWorkbook();

2.创建Excel文件,并写入数据


//创建工作簿 HSSFWorkbook wk = new HSSFWorkbook(); //创建名称为mySheet的表 ISheet tb = wk.CreateSheet("mySheet"); //创建第一行,此行为第二行 IRow row = tb.CreateRow(1); for (int i = 0; i < 20; i++) {     ICell cell = row.CreateCell(i); //创建单元格,写入数据     cell.SetCellValue(i); }  //保存到文件 //打开一个xls文件,如果没有自行创建 //如果存在则重新创建 using (FileStream fs = File.OpenWrite(LocalPathHelper.GetCurrentData() + "\\testone.xls")) {     wk.Write(fs);     Console.WriteLine("导出数据成功!"); }


3.创建Excel文件并设置单元格样式

.Net Excel操作之NPOI(一)简介_封装_04.Net Excel操作之NPOI(一)简介_c#_05

/// <summary> /// 创建xml 常用操作 /// </summary> public static void TestTwo() {     IWorkbook wb = new HSSFWorkbook();     //创建表       ISheet sh = wb.CreateSheet("zhiyuan");     //设置单元的宽度       sh.SetColumnWidth(0, 15 * 256);     sh.SetColumnWidth(1, 35 * 256);     sh.SetColumnWidth(2, 15 * 256);     sh.SetColumnWidth(3, 10 * 256);     int i = 0;      #region 练习合并单元格     sh.AddMergedRegion(new NPOI.SS.Util.CellRangeAddress(0, 0, 0, 3));     //CellRangeAddress()该方法的参数次序是:开始行号,结束行号,开始列号,结束列号。     IRow row0 = sh.CreateRow(0);     row0.Height = 20 * 20;     ICell icell1top0 = row0.CreateCell(0);     icell1top0.CellStyle = Getcellstyle(wb, stylexls.头);     icell1top0.SetCellValue("标题合并单元");     #endregion      i++;     #region 设置表头     IRow row1 = sh.CreateRow(1);     row1.Height = 20 * 20;      ICell icell1top = row1.CreateCell(0);     icell1top.CellStyle = Getcellstyle(wb, stylexls.头);     icell1top.SetCellValue("网站名");      ICell icell2top = row1.CreateCell(1);     icell2top.CellStyle = Getcellstyle(wb, stylexls.头);     icell2top.SetCellValue("网址");      ICell icell3top = row1.CreateCell(2);     icell3top.CellStyle = Getcellstyle(wb, stylexls.头);     icell3top.SetCellValue("百度快照");      ICell icell4top = row1.CreateCell(3);     icell4top.CellStyle = Getcellstyle(wb, stylexls.头);     icell4top.SetCellValue("百度收录");     #endregion      using (FileStream stm = File.OpenWrite(LocalPathHelper.GetCurrentData() + "\\site.xls"))     {         wb.Write(stm);         Console.WriteLine("导出数据成功");     } } #region 定义单元格常用到样式的枚举 public enum stylexls {     头,     url,     时间,     数字,     钱,     百分比,     中文大写,     科学计数法,     默认 } #endregion #region 定义单元格常用到样式 static ICellStyle Getcellstyle(IWorkbook wb, stylexls str) {     ICellStyle cellStyle = wb.CreateCellStyle();      //定义几种字体       //也可以一种字体,写一些公共属性,然后在下面需要时加特殊的       IFont font12 = wb.CreateFont();     font12.FontHeightInPoints = 12;     font12.FontName = "微软雅黑";       IFont font = wb.CreateFont();     font.FontName = "微软雅黑";     //font.Underline = 1;下划线         IFont fontcolorblue = wb.CreateFont();     fontcolorblue.Color = HSSFColor.OliveGreen.Blue.Index;     fontcolorblue.IsItalic = true;//下划线       fontcolorblue.FontName = "微软雅黑";       //边框       cellStyle.BorderBottom = NPOI.SS.UserModel.BorderStyle.Dotted;     cellStyle.BorderLeft = NPOI.SS.UserModel.BorderStyle.Hair;     cellStyle.BorderRight = NPOI.SS.UserModel.BorderStyle.Hair;     cellStyle.BorderTop = NPOI.SS.UserModel.BorderStyle.Dotted;     //边框颜色       cellStyle.BottomBorderColor = HSSFColor.OliveGreen.Blue.Index;     cellStyle.TopBorderColor = HSSFColor.OliveGreen.Blue.Index;      //背景图形,我没有用到过。感觉很丑       cellStyle.FillForegroundColor = HSSFColor.White.Index;     // cellStyle.FillPattern = FillPatternType.NO_FILL;       cellStyle.FillBackgroundColor = HSSFColor.Blue.Index;      //水平对齐       cellStyle.Alignment = NPOI.SS.UserModel.HorizontalAlignment.Left;      //垂直对齐       cellStyle.VerticalAlignment = VerticalAlignment.Center;      //自动换行       cellStyle.WrapText = true;      //缩进;当设置为1时,前面留的空白太大了。希旺官网改进。或者是我设置的不对       cellStyle.Indention = 0;      //上面基本都是设共公的设置       //下面列出了常用的字段类型       switch (str)     {         case stylexls.头:             // cellStyle.FillPattern = FillPatternType.LEAST_DOTS;               cellStyle.SetFont(font12);             break;         case stylexls.时间:             IDataFormat datastyle = wb.CreateDataFormat();              cellStyle.DataFormat = datastyle.GetFormat("yyyy/mm/dd");             cellStyle.SetFont(font);             break;         case stylexls.数字:             cellStyle.DataFormat = HSSFDataFormat.GetBuiltinFormat("0.00");             cellStyle.SetFont(font);             break;         case stylexls.钱:             IDataFormat format = wb.CreateDataFormat();             cellStyle.DataFormat = format.GetFormat("¥#,##0");             cellStyle.SetFont(font);             break;         case stylexls.url:             fontcolorblue.Underline = FontUnderlineType.Single;             cellStyle.SetFont(fontcolorblue);             break;         case stylexls.百分比:             cellStyle.DataFormat = HSSFDataFormat.GetBuiltinFormat("0.00%");             cellStyle.SetFont(font);             break;         case stylexls.中文大写:             IDataFormat format1 = wb.CreateDataFormat();             cellStyle.DataFormat = format1.GetFormat("[DbNum2][$-804]0");             cellStyle.SetFont(font);             break;         case stylexls.科学计数法:             cellStyle.DataFormat = HSSFDataFormat.GetBuiltinFormat("0.00E+00");             cellStyle.SetFont(font);             break;         case stylexls.默认:             cellStyle.SetFont(font);             break;     }     return cellStyle;   } #endregion

View Code

4.读取Excel文件数据


StringBuilder sbr = new StringBuilder();         using (FileStream fs = File.OpenRead(LocalPathHelper.GetCurrentData() + "\\site.xls"))         {             HSSFWorkbook wk = new HSSFWorkbook(fs);//读取xls文件中的数据写入wk中             for (int i = 0; i < wk.NumberOfSheets; i++) //NumberOfSheets是总共的表数              {                 ISheet sheet = wk.GetSheetAt(i); //读取当前表数据                 for (int j = 0; j <= sheet.LastRowNum; j++) //LastRowNum 最后一行的索引,从0开始                 {                     IRow row = sheet.GetRow(j);//获取当前行数据                     if (row != null)                     {                         sbr.Append("\r\n--------------------------------\r\n");                         for (int k = 0; k <= row.LastCellNum; k++) //LastCellNum 最后一列的索引,从0开始                         {                             ICell cell = row.GetCell(k); //获取当前单元格                             if (cell != null)                             {                                 sbr.Append(cell.ToString() + "\t");                             }                         }                     }                 }             }          }          //将读取的Xml文件数据写入到txt中         using (StreamWriter sw = new StreamWriter(new FileStream(LocalPathHelper.GetCurrentData() + "\\test1.txt", FileMode.Append)))         {             sw.Write(sbr.ToString());             sw.Flush();             Console.WriteLine("读取数据成功!");         }


.Net Excel操作之NPOI(一)简介_.Net Excel操作之NPOI_06


MissingCellPolicy 枚举

如果你在一行中迭代列,一些空白的单元格甚至可能不存在,这可能导致毫无疑问的代码抛出一个​​NullPointerException​​​.A ​​MissingCellPolicy​​​,当传递给它时​​getCell​​,引导并简化代码,告诉Apache POI如何处理这些类型的单元格.


ICell cell1 = row.GetCell(0,MissingCellPolicy.RETURN_BLANK_AS_NULL);