C#读取Excel几种方法的体会

开发 后端 开发工具
本文详细介绍了C#的三种读取Excel的方法,通过对有点和缺点的分析,让网友有着更多的选择。

(1) OleDb: 用这种方法读取Excel速度还是非常的快的,但这种方式读取数据的时候不太灵活,不过可以在 DataTable 中对数据进行一些删减修改

这种方式将Excel作为一个数据源,直接用Sql语句获取数据了。所以读取之前要知道此次要读取的Sheet(当然也可以用序号,类似dt.Row[0][0]。这样倒是不需要知道Sheet)
?

if (fileType == ".xls")  
   connStr = "Provider=Microsoft.Jet.OLEDB.4.0;" + "Data Source=" + fileName + ";" + ";Extended Properties=\"Excel 8.0;HDR=YES;IMEX=1\"";  
else 
   connStr = "Provider=Microsoft.ACE.OLEDB.12.0;" + "Data Source=" + fileName + ";" + ";Extended Properties=\"Excel 12.0;HDR=YES;IMEX=1\"";  
   
OleDbConnection conn new OleDbConnection(connStr);  
DataTable dtSheetName = conn.GetOleDbSchemaTable(OleDbSchemaGuid.Tables, new object[] { nullnullnull"TABLE" }); 
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.

以上是读取Excel的Sheet名,xls和xlsx的连接字符串也不一样的,可以根据文件的后缀来区别。这里需要注意的一点,Excel里面只有一个Sheet,但通过这种方式读取Sheet可能会大于一个。原因已经有人在别的网站说过了,偷一下懒O(∩_∩)O,下面文段来自【cdwolfling

【在使用过程中发现取出的Sheet和实际excel不一致, 会多出不少。目前总结后有两种情况:

1. 取出的名称中,包括了XL命名管理器中的名称(参见XL2007的公式--命名管理器, 快捷键Crtl+F3);

2. 取出的名称中,包括了FilterDatabase后缀的, 这是XL用来记录Filter范围的,  参见http://www.mrexcel.com/forum/showthread.php?t=27225

对于***点比较简单, 删除已有命名管理器中的内容即可;第二点处理起来比较麻烦, Filter删除后这些名称依然保留着,简单的做法是新增sheet然后将原sheet Copy进去】

---------------------------------

但实际情况并不能为每个Excel做以上检查【cdwolfling】也给出了过滤的方案,当时还是有点问题,本来补充了一点。总之先看代码吧

for (int i = 0; i < dtSheetName.Rows.Count; i++)  
 
{  
?  
SheetName = (string)dtSheetName.Rows[i]["TABLE_NAME"];  
   
if (SheetName .Contains("$") && !SheetName .Replace("'""").EndsWith("$"))continue;//过滤无效SheetName完毕....  
 
da.SelectCommand = new OleDbCommand(String.Format(sql_F, tblName), conn);  
DataSet dsItem = new DataSet();  
da.Fill(dsItem, tblName);  
?  

  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.

因为读取出来无效SheetName一般情况***一个字符都不会是$。如果SheetName有一些特殊符号,读取出来的SheetName会自动加上单引号,比如在Excel中将SheetName编辑成:MySheet(1),此时读取出来的SheetName就为:'MySheet(1)$',所以判断***一个字符是不是$之前***过滤一下单引号。

优点:读取方式简单、读取速度快

缺点:除了读取过程不太灵活之外,这种读取方式还有个弊端就是,当Excel数据量很大时。会非常占用内存,当内存不够时会抛出内存溢出的异常。

不过一般情况下还是非常不错的

读取Excel完整代码:

/// <summary>  
        /// 读取Excel文件到DataSet中  
        /// </summary>  
        /// <param name="filePath">文件路径</param>  
        /// <returns></returns>  
        public static DataSet ToDataTable(string filePath)  
        {  
            string connStr = "";             
            string fileType = System.IO.Path.GetExtension(fileName);  
            if (string.IsNullOrEmpty(fileType)) return null;  
   
            if (fileType == ".xls")  
                connStr = "Provider=Microsoft.Jet.OLEDB.4.0;" + "Data Source=" + filePath+ ";" + ";Extended Properties=\"Excel 8.0;HDR=YES;IMEX=1\"";  
            else 
                connStr = "Provider=Microsoft.ACE.OLEDB.12.0;" + "Data Source=" + filePath+ ";" + ";Extended Properties=\"Excel 12.0;HDR=YES;IMEX=1\"";  
            string sql_F = "Select * FROM [{0}]";  
   
            OleDbConnection conn = null;  
            OleDbDataAdapter da = null;  
            DataTable dtSheetName= null;  
   
            DataSet ds = new DataSet();  
            try 
            {  
                // 初始化连接,并打开  
                conn = new OleDbConnection(connStr);  
                conn.Open();  
   
                // 获取数据源的表定义元数据                         
                string SheetName = "";  
                dtSheetName= conn.GetOleDbSchemaTable(OleDbSchemaGuid.Tables, new object[] { nullnullnull"TABLE" });  
   
                // 初始化适配器  
                da = new OleDbDataAdapter();  
                for (int i = 0; i < dtSheetName.Rows.Count; i++)  
                {  
                    SheetName = (string)dtSheetName.Rows[i]["TABLE_NAME"];  
   
                    if (SheetName .Contains("$") && !SheetName .Replace("'""").EndsWith("$"))  
                    {  
                        continue;  
                    }  
   
                    da.SelectCommand = new OleDbCommand(String.Format(sql_F, SheetName ), conn);  
                    DataSet dsItem = new DataSet();  
                    da.Fill(dsItem, tblName);  
   
                    ds.Tables.Add(dsItem.Tables[0].Copy());  
                }  
            }  
            catch (Exception ex)  
            {  
            }  
            finally 
            {  
                // 关闭连接  
                if (conn.State == ConnectionState.Open)  
                {  
                    conn.Close();  
                    da.Dispose();  
                    conn.Dispose();  
                }  
            }  
            return ds;  
        } 
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
  • 14.
  • 15.
  • 16.
  • 17.
  • 18.
  • 19.
  • 20.
  • 21.
  • 22.
  • 23.
  • 24.
  • 25.
  • 26.
  • 27.
  • 28.
  • 29.
  • 30.
  • 31.
  • 32.
  • 33.
  • 34.
  • 35.
  • 36.
  • 37.
  • 38.
  • 39.
  • 40.
  • 41.
  • 42.
  • 43.
  • 44.
  • 45.
  • 46.
  • 47.
  • 48.
  • 49.
  • 50.
  • 51.
  • 52.
  • 53.
  • 54.
  • 55.
  • 56.
  • 57.
  • 58.
  • 59.
  • 60.
  • 61.
  • 62.
  • 63.
  • 64.
  • 65.

#p#

(2):Com组件的方式读取Excel

这种方式需要先引用 Microsoft.Office.Interop.Excel 。***说下这种方式的优缺点

优点:可以非常灵活的读取Excel中的数据

缺点:如果是Web站点部署在IIS上时,还需要服务器机子已安装了Excel,有时候还需要为配置IIS权限。最重要的一点因为是基于单元格方式读取的,所以数据很慢(曾做过试验,直接读取千行、200多列的文件,直接读取耗时15分钟。即使采用多线程分段读取来提高CPU的利用率也需要8分钟。PS:CPU I3)

需要读取大文件的的童鞋们慎重。。。

附上单线程和多线程读取类:

public class ExcelOptions  
    {  
        private Stopwatch wath = new Stopwatch();  
   
        /// <summary>  
        /// 使用COM读取Excel  
        /// </summary>  
        /// <param name="excelFilePath">路径</param>  
        /// <returns>DataTabel</returns>  
        public System.Data.DataTable GetExcelData(string excelFilePath)  
        {  
            Excel.Application app = new Excel.Application();  
            Excel.Sheets sheets;  
            Excel.Workbook workbook = null;  
            object oMissiong = System.Reflection.Missing.Value;  
            System.Data.DataTable dt = new System.Data.DataTable();  
   
            wath.Start();  
   
            try 
            {  
                if (app == null)  
                {  
                    return null;  
                }  
   
                workbook = app.Workbooks.Open(excelFilePath, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong);  
   
                //将数据读入到DataTable中——Start    
   
                sheets = workbook.Worksheets;  
                Excel.Worksheet worksheet = (Excel.Worksheet)sheets.get_Item(1);//读取***张表  
                if (worksheet == null)  
                    return null;  
   
                string cellContent;  
                int iRowCount = worksheet.UsedRange.Rows.Count;  
                int iColCount = worksheet.UsedRange.Columns.Count;  
                Excel.Range range;  
   
                //负责列头Start  
                DataColumn dc;  
                int ColumnID = 1;  
                range = (Excel.Range)worksheet.Cells[1, 1];  
                while (range.Text.ToString().Trim() != "")  
                {  
                    dc = new DataColumn();  
                    dc.DataType = System.Type.GetType("System.String");  
                    dc.ColumnName = range.Text.ToString().Trim();  
                    dt.Columns.Add(dc);  
   
                    range = (Excel.Range)worksheet.Cells[1, ++ColumnID];  
                }  
                //End  
   
                for (int iRow = 2; iRow <= iRowCount; iRow++)  
                {  
                    DataRow dr = dt.NewRow();  
   
                    for (int iCol = 1; iCol <= iColCount; iCol++)  
                    {  
                        range = (Excel.Range)worksheet.Cells[iRow, iCol];  
   
                        cellContent = (range.Value2 == null) ? "" : range.Text.ToString();  
   
                        //if (iRow == 1)  
                        //{  
                        //    dt.Columns.Add(cellContent);  
                        //}  
                        //else  
                        //{  
                            dr[iCol - 1] = cellContent;  
                        //}  
                    }  
   
                    //if (iRow != 1)  
                    dt.Rows.Add(dr);  
                }  
   
                wath.Stop();  
                TimeSpan ts = wath.Elapsed;  
   
                //将数据读入到DataTable中——End  
                return dt;  
            }  
            catch 
            {  
                   
                return null;  
            }  
            finally 
            {  
                workbook.Close(false, oMissiong, oMissiong);  
                System.Runtime.InteropServices.Marshal.ReleaseComObject(workbook);  
                workbook = null;  
                app.Workbooks.Close();  
                app.Quit();  
                System.Runtime.InteropServices.Marshal.ReleaseComObject(app);  
                app = null;  
                GC.Collect();  
                GC.WaitForPendingFinalizers();  
            }  
        }  
   
   
        /// <summary>  
        /// 使用COM,多线程读取Excel(1 主线程、4 副线程)  
        /// </summary>  
        /// <param name="excelFilePath">路径</param>  
        /// <returns>DataTabel</returns>  
        public System.Data.DataTable ThreadReadExcel(string excelFilePath)  
        {  
            Excel.Application app = new Excel.Application();  
            Excel.Sheets sheets = null;  
            Excel.Workbook workbook = null;  
            object oMissiong = System.Reflection.Missing.Value;  
            System.Data.DataTable dt = new System.Data.DataTable();  
   
            wath.Start();  
   
            try 
            {  
                if (app == null)  
                {  
                    return null;  
                }  
   
                workbook = app.Workbooks.Open(excelFilePath, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong);  
   
                //将数据读入到DataTable中——Start    
                sheets = workbook.Worksheets;  
                Excel.Worksheet worksheet = (Excel.Worksheet)sheets.get_Item(1);//读取***张表  
                if (worksheet == null)  
                    return null;  
   
                string cellContent;  
                int iRowCount = worksheet.UsedRange.Rows.Count;  
                int iColCount = worksheet.UsedRange.Columns.Count;  
                Excel.Range range;  
   
                //负责列头Start  
                DataColumn dc;  
                int ColumnID = 1;  
                range = (Excel.Range)worksheet.Cells[1, 1];  
                //while (range.Text.ToString().Trim() != "")  
                while (iColCount >= ColumnID)  
                {  
                    dc = new DataColumn();  
                    dc.DataType = System.Type.GetType("System.String");  
   
                    string strNewColumnName = range.Text.ToString().Trim();  
                    if (strNewColumnName.Length == 0) strNewColumnName = "_1";  
                    //判断列名是否重复  
                    for (int i = 1; i < ColumnID; i++)  
                    {  
                        if (dt.Columns[i - 1].ColumnName == strNewColumnName)  
                            strNewColumnName = strNewColumnName + "_1";  
                    }  
   
                    dc.ColumnName = strNewColumnName;  
                    dt.Columns.Add(dc);  
   
                    range = (Excel.Range)worksheet.Cells[1, ++ColumnID];  
                }  
                //End  
   
                //数据大于500条,使用多进程进行读取数据  
                if (iRowCount - 1 > 500)  
                {  
                    //开始多线程读取数据  
                    //新建线程  
                    int b2 = (iRowCount - 1) / 10;  
                    DataTable dt1 = new DataTable("dt1");  
                    dt1 = dt.Clone();  
                    SheetOptions sheet1thread = new SheetOptions(worksheet, iColCount, 2, b2 + 1, dt1);  
                    Thread othread1 = new Thread(new ThreadStart(sheet1thread.SheetToDataTable));  
                    othread1.Start();  
   
                    //阻塞 1 毫秒,保证***个读取 dt1  
                    Thread.Sleep(1);  
   
                    DataTable dt2 = new DataTable("dt2");  
                    dt2 = dt.Clone();  
                    SheetOptions sheet2thread = new SheetOptions(worksheet, iColCount, b2 + 2, b2 * 2 + 1, dt2);  
                    Thread othread2 = new Thread(new ThreadStart(sheet2thread.SheetToDataTable));  
                    othread2.Start();  
   
                    DataTable dt3 = new DataTable("dt3");  
                    dt3 = dt.Clone();  
                    SheetOptions sheet3thread = new SheetOptions(worksheet, iColCount, b2 * 2 + 2, b2 * 3 + 1, dt3);  
                    Thread othread3 = new Thread(new ThreadStart(sheet3thread.SheetToDataTable));  
                    othread3.Start();  
   
                    DataTable dt4 = new DataTable("dt4");  
                    dt4 = dt.Clone();  
                    SheetOptions sheet4thread = new SheetOptions(worksheet, iColCount, b2 * 3 + 2, b2 * 4 + 1, dt4);  
                    Thread othread4 = new Thread(new ThreadStart(sheet4thread.SheetToDataTable));  
                    othread4.Start();  
   
                    //主线程读取剩余数据  
                    for (int iRow = b2 * 4 + 2; iRow <= iRowCount; iRow++)  
                    {  
                        DataRow dr = dt.NewRow();  
                        for (int iCol = 1; iCol <= iColCount; iCol++)  
                        {  
                            range = (Excel.Range)worksheet.Cells[iRow, iCol];  
                            cellContent = (range.Value2 == null) ? "" : range.Text.ToString();  
                            dr[iCol - 1] = cellContent;  
                        }  
                        dt.Rows.Add(dr);  
                    }  
   
                    othread1.Join();  
                    othread2.Join();  
                    othread3.Join();  
                    othread4.Join();  
   
                    //将多个线程读取出来的数据追加至 dt1 后面  
                    foreach (DataRow dr in dt.Rows)  
                        dt1.Rows.Add(dr.ItemArray);  
                    dt.Clear();  
                    dt.Dispose();  
   
                    foreach (DataRow dr in dt2.Rows)  
                        dt1.Rows.Add(dr.ItemArray);  
                    dt2.Clear();  
                    dt2.Dispose();  
   
                    foreach (DataRow dr in dt3.Rows)  
                        dt1.Rows.Add(dr.ItemArray);  
                    dt3.Clear();  
                    dt3.Dispose();  
   
                    foreach (DataRow dr in dt4.Rows)  
                        dt1.Rows.Add(dr.ItemArray);  
                    dt4.Clear();  
                    dt4.Dispose();  
   
                    return dt1;  
                }  
                else 
                {  
                    for (int iRow = 2; iRow <= iRowCount; iRow++)  
                    {  
                        DataRow dr = dt.NewRow();  
                        for (int iCol = 1; iCol <= iColCount; iCol++)  
                        {  
                            range = (Excel.Range)worksheet.Cells[iRow, iCol];  
                            cellContent = (range.Value2 == null) ? "" : range.Text.ToString();  
                            dr[iCol - 1] = cellContent;  
                        }  
                        dt.Rows.Add(dr);  
                    }  
                }  
   
                wath.Stop();  
                TimeSpan ts = wath.Elapsed;  
                //将数据读入到DataTable中——End  
                return dt;  
            }  
            catch 
            {  
   
                return null;  
            }  
            finally 
            {  
                workbook.Close(false, oMissiong, oMissiong);  
                System.Runtime.InteropServices.Marshal.ReleaseComObject(workbook);  
                System.Runtime.InteropServices.Marshal.ReleaseComObject(sheets);  
                workbook = null;  
                app.Workbooks.Close();  
                app.Quit();  
                System.Runtime.InteropServices.Marshal.ReleaseComObject(app);  
                app = null;  
                GC.Collect();  
                GC.WaitForPendingFinalizers();  
                   
                /*  
                object objmissing = System.Reflection.Missing.Value;  
   
Excel.ApplicationClass application = new ApplicationClass();  
Excel.Workbook book = application.Workbooks.Add(objmissing);  
Excel.Worksheet sheet = (Excel.Worksheet)book.Worksheets.Add(objmissing,objmissing,objmissing,objmissing);  
   
//操作过程 ^&%&×&……&%&&……  
   
//释放  
sheet.SaveAs(path,objmissing,objmissing,objmissing,objmissing,objmissing,objmissing,objmissing,objmissing);  
System.Runtime.InteropServices.Marshal.ReleaseComObject((object)sheet);  
System.Runtime.InteropServices.Marshal.ReleaseComObject((object)book);  
application.Quit();  
System.Runtime.InteropServices.Marshal.ReleaseComObject((object)application);  
System.GC.Collect();  
                 */ 
            }  
        }  
   
   
        /// <summary>  
        /// 删除Excel行  
        /// </summary>  
        /// <param name="excelFilePath">Excel路径</param>  
        /// <param name="rowStart">开始行</param>  
        /// <param name="rowEnd">结束行</param>  
        /// <param name="designationRow">指定行</param>  
        /// <returns></returns>  
        public string DeleteRows(string excelFilePath, int rowStart, int rowEnd, int designationRow)  
        {  
            string result = "";  
            Excel.Application app = new Excel.Application();  
            Excel.Sheets sheets;  
            Excel.Workbook workbook = null;  
            object oMissiong = System.Reflection.Missing.Value;  
            try 
            {  
                if (app == null)  
                {  
                    return "分段读取Excel失败";  
                }  
   
                workbook = app.Workbooks.Open(excelFilePath, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong, oMissiong);  
                sheets = workbook.Worksheets;  
                Excel.Worksheet worksheet = (Excel.Worksheet)sheets.get_Item(1);//读取***张表  
                if (worksheet == null)  
                    return result;  
                Excel.Range range;  
   
                //先删除指定行,一般为列描述  
                if (designationRow != -1)  
                {  
                    range = (Excel.Range)worksheet.Rows[designationRow, oMissiong];  
                    range.Delete(Excel.XlDeleteShiftDirection.xlShiftUp);  
                }  
                Stopwatch sw = new Stopwatch();  
                sw.Start();  
   
                int i = rowStart;  
                for (int iRow = rowStart; iRow <= rowEnd; iRow++, i++)  
                {  
                    range = (Excel.Range)worksheet.Rows[rowStart, oMissiong];  
                    range.Delete(Excel.XlDeleteShiftDirection.xlShiftUp);  
                }  
   
                sw.Stop();  
                TimeSpan ts = sw.Elapsed;  
                workbook.Save();  
   
                //将数据读入到DataTable中——End  
                return result;  
            }  
            catch 
            {  
   
                return "分段读取Excel失败";  
            }  
            finally 
            {  
                workbook.Close(false, oMissiong, oMissiong);  
                System.Runtime.InteropServices.Marshal.ReleaseComObject(workbook);  
                workbook = null;  
                app.Workbooks.Close();  
                app.Quit();  
                System.Runtime.InteropServices.Marshal.ReleaseComObject(app);  
                app = null;  
                GC.Collect();  
                GC.WaitForPendingFinalizers();  
            }  
        }  
   
        public void ToExcelSheet(DataSet ds, string fileName)  
        {  
            Excel.Application appExcel = new Excel.Application();  
            Excel.Workbook workbookData = null;  
            Excel.Worksheet worksheetData;  
            Excel.Range range;  
            try 
            {  
                workbookData = appExcel.Workbooks.Add(System.Reflection.Missing.Value);  
                appExcel.DisplayAlerts = false;//不显示警告  
                //xlApp.Visible = true;//excel是否可见  
                //  
                //for (int i = workbookData.Worksheets.Count; i > 0; i--)  
                //{  
                //    Microsoft.Office.Interop.Excel.Worksheet oWorksheet = (Microsoft.Office.Interop.Excel.Worksheet)workbookData.Worksheets.get_Item(i);  
                //    oWorksheet.Select();  
                //    oWorksheet.Delete();  
                //}  
   
                for (int k = 0; k < ds.Tables.Count; k++)  
                {  
                    worksheetData = (Excel.Worksheet)workbookData.Worksheets.Add(System.Reflection.Missing.Value, System.Reflection.Missing.Value, System.Reflection.Missing.Value, System.Reflection.Missing.Value);  
                    // testnum--;  
                    if (ds.Tables[k] != null)  
                    {  
                        worksheetData.Name = ds.Tables[k].TableName;  
                        //写入标题  
                        for (int i = 0; i < ds.Tables[k].Columns.Count; i++)  
                        {  
                            worksheetData.Cells[1, i + 1] = ds.Tables[k].Columns[i].ColumnName;  
                            range = (Excel.Range)worksheetData.Cells[1, i + 1];  
                            //range.Interior.ColorIndex = 15;  
                            range.Font.Bold = true;  
                            range.NumberFormatLocal = "@";//文本格式  
                            range.EntireColumn.AutoFit();//自动调整列宽  
                            // range.WrapText = true; //文本自动换行    
                            range.ColumnWidth = 15;  
                        }  
                        //写入数值  
                        for (int r = 0; r < ds.Tables[k].Rows.Count; r++)  
                        {  
                            for (int i = 0; i < ds.Tables[k].Columns.Count; i++)  
                            {  
                                worksheetData.Cells[r + 2, i + 1] = ds.Tables[k].Rows[r][i];  
                                //Range myrange = worksheetData.get_Range(worksheetData.Cells[r + 2, i + 1], worksheetData.Cells[r + 3, i + 2]);  
                                //myrange.NumberFormatLocal = "@";//文本格式  
                                //// myrange.EntireColumn.AutoFit();//自动调整列宽  
                                ////   myrange.WrapText = true; //文本自动换行    
                                //myrange.ColumnWidth = 15;  
                            }  
                            //  rowRead++;  
                            //System.Windows.Forms.Application.DoEvents();  
                        }  
                    }  
                    worksheetData.Columns.EntireColumn.AutoFit();  
                    workbookData.Saved = true;  
                }  
            }  
            catch (Exception ex) { }  
            finally 
            {  
                workbookData.SaveCopyAs(fileName);  
                workbookData.Close(false, System.Reflection.Missing.Value, System.Reflection.Missing.Value);  
                appExcel.Quit();  
                GC.Collect();  
            }  
        }  
       
    } 
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
  • 14.
  • 15.
  • 16.
  • 17.
  • 18.
  • 19.
  • 20.
  • 21.
  • 22.
  • 23.
  • 24.
  • 25.
  • 26.
  • 27.
  • 28.
  • 29.
  • 30.
  • 31.
  • 32.
  • 33.
  • 34.
  • 35.
  • 36.
  • 37.
  • 38.
  • 39.
  • 40.
  • 41.
  • 42.
  • 43.
  • 44.
  • 45.
  • 46.
  • 47.
  • 48.
  • 49.
  • 50.
  • 51.
  • 52.
  • 53.
  • 54.
  • 55.
  • 56.
  • 57.
  • 58.
  • 59.
  • 60.
  • 61.
  • 62.
  • 63.
  • 64.
  • 65.
  • 66.
  • 67.
  • 68.
  • 69.
  • 70.
  • 71.
  • 72.
  • 73.
  • 74.
  • 75.
  • 76.
  • 77.
  • 78.
  • 79.
  • 80.
  • 81.
  • 82.
  • 83.
  • 84.
  • 85.
  • 86.
  • 87.
  • 88.
  • 89.
  • 90.
  • 91.
  • 92.
  • 93.
  • 94.
  • 95.
  • 96.
  • 97.
  • 98.
  • 99.
  • 100.
  • 101.
  • 102.
  • 103.
  • 104.
  • 105.
  • 106.
  • 107.
  • 108.
  • 109.
  • 110.
  • 111.
  • 112.
  • 113.
  • 114.
  • 115.
  • 116.
  • 117.
  • 118.
  • 119.
  • 120.
  • 121.
  • 122.
  • 123.
  • 124.
  • 125.
  • 126.
  • 127.
  • 128.
  • 129.
  • 130.
  • 131.
  • 132.
  • 133.
  • 134.
  • 135.
  • 136.
  • 137.
  • 138.
  • 139.
  • 140.
  • 141.
  • 142.
  • 143.
  • 144.
  • 145.
  • 146.
  • 147.
  • 148.
  • 149.
  • 150.
  • 151.
  • 152.
  • 153.
  • 154.
  • 155.
  • 156.
  • 157.
  • 158.
  • 159.
  • 160.
  • 161.
  • 162.
  • 163.
  • 164.
  • 165.
  • 166.
  • 167.
  • 168.
  • 169.
  • 170.
  • 171.
  • 172.
  • 173.
  • 174.
  • 175.
  • 176.
  • 177.
  • 178.
  • 179.
  • 180.
  • 181.
  • 182.
  • 183.
  • 184.
  • 185.
  • 186.
  • 187.
  • 188.
  • 189.
  • 190.
  • 191.
  • 192.
  • 193.
  • 194.
  • 195.
  • 196.
  • 197.
  • 198.
  • 199.
  • 200.
  • 201.
  • 202.
  • 203.
  • 204.
  • 205.
  • 206.
  • 207.
  • 208.
  • 209.
  • 210.
  • 211.
  • 212.
  • 213.
  • 214.
  • 215.
  • 216.
  • 217.
  • 218.
  • 219.
  • 220.
  • 221.
  • 222.
  • 223.
  • 224.
  • 225.
  • 226.
  • 227.
  • 228.
  • 229.
  • 230.
  • 231.
  • 232.
  • 233.
  • 234.
  • 235.
  • 236.
  • 237.
  • 238.
  • 239.
  • 240.
  • 241.
  • 242.
  • 243.
  • 244.
  • 245.
  • 246.
  • 247.
  • 248.
  • 249.
  • 250.
  • 251.
  • 252.
  • 253.
  • 254.
  • 255.
  • 256.
  • 257.
  • 258.
  • 259.
  • 260.
  • 261.
  • 262.
  • 263.
  • 264.
  • 265.
  • 266.
  • 267.
  • 268.
  • 269.
  • 270.
  • 271.
  • 272.
  • 273.
  • 274.
  • 275.
  • 276.
  • 277.
  • 278.
  • 279.
  • 280.
  • 281.
  • 282.
  • 283.
  • 284.
  • 285.
  • 286.
  • 287.
  • 288.
  • 289.
  • 290.
  • 291.
  • 292.
  • 293.
  • 294.
  • 295.
  • 296.
  • 297.
  • 298.
  • 299.
  • 300.
  • 301.
  • 302.
  • 303.
  • 304.
  • 305.
  • 306.
  • 307.
  • 308.
  • 309.
  • 310.
  • 311.
  • 312.
  • 313.
  • 314.
  • 315.
  • 316.
  • 317.
  • 318.
  • 319.
  • 320.
  • 321.
  • 322.
  • 323.
  • 324.
  • 325.
  • 326.
  • 327.
  • 328.
  • 329.
  • 330.
  • 331.
  • 332.
  • 333.
  • 334.
  • 335.
  • 336.
  • 337.
  • 338.
  • 339.
  • 340.
  • 341.
  • 342.
  • 343.
  • 344.
  • 345.
  • 346.
  • 347.
  • 348.
  • 349.
  • 350.
  • 351.
  • 352.
  • 353.
  • 354.
  • 355.
  • 356.
  • 357.
  • 358.
  • 359.
  • 360.
  • 361.
  • 362.
  • 363.
  • 364.
  • 365.
  • 366.
  • 367.
  • 368.
  • 369.
  • 370.
  • 371.
  • 372.
  • 373.
  • 374.
  • 375.
  • 376.
  • 377.
  • 378.
  • 379.
  • 380.
  • 381.
  • 382.
  • 383.
  • 384.
  • 385.
  • 386.
  • 387.
  • 388.
  • 389.
  • 390.
  • 391.
  • 392.
  • 393.
  • 394.
  • 395.
  • 396.
  • 397.
  • 398.
  • 399.
  • 400.
  • 401.
  • 402.
  • 403.
  • 404.
  • 405.
  • 406.
  • 407.
  • 408.
  • 409.
  • 410.
  • 411.
  • 412.
  • 413.
  • 414.
  • 415.
  • 416.
  • 417.
  • 418.
  • 419.
  • 420.
  • 421.
  • 422.
  • 423.
  • 424.
  • 425.
  • 426.
  • 427.
  • 428.
  • 429.
  • 430.
  • 431.
  • 432.
  • 433.
  • 434.
  • 435.
  • 436.
  • 437.
  • 438.
  • 439.

#p#

(3)NPOI方式读取Excel,NPOI是一组开源的组件,类似Java的 POI。包括:NPOI、NPOI.HPSF、NPOI.HSSF、NPOI.HSSF.UserModel、NPOI.POIFS、NPOI.Util,下载的时候别只下一个噢

 

优点:读取Excel速度较快,读取方式操作灵活性

缺点:只支持03的Excel,xlsx的无法读取。由于这点,使用这种方式的人不多啊,没理由要求客户使用03版Excel吧,再说03版Excel对于行数还有限制,只支持65536行。

(听他们的开发人员说会在2012年底推出新版,支持xlsx的读取。但一直很忙没时间去关注这个事情,有兴趣的同学可以瞧瞧去)

NPOI读取Excel类:

using System;  
using System.Data;  
using System.IO;  
using System.Web;  
using NPOI;  
using NPOI.HPSF;  
using NPOI.HSSF;  
using NPOI.HSSF.UserModel;  
using NPOI.POIFS;  
using NPOI.Util;  
using System.Text;  
using System.Configuration;  
   
public class NPOIHelper  
{  
    private static int ExcelMaxRow = Convert.ToInt32(ConfigurationManager.AppSettings["ExcelMaxRow"]);  
    /// <summary>  
    /// 由DataSet导出Excel  
    /// </summary>  
    /// <param name="sourceTable">要导出数据的DataTable</param>     
    /// <param name="sheetName">工作表名称</param>  
    /// <returns>Excel工作表</returns>     
    private static Stream ExportDataSetToExcel(DataSet sourceDs)  
    {  
        HSSFWorkbook workbook = new HSSFWorkbook();  
        MemoryStream ms = new MemoryStream();  
   
        for (int i = 0; i < sourceDs.Tables.Count; i++)  
        {  
            HSSFSheet sheet = (HSSFSheet)workbook.CreateSheet(sourceDs.Tables[i].TableName);  
            HSSFRow headerRow = (HSSFRow)sheet.CreateRow(0);  
            // handling header.             
            foreach (DataColumn column in sourceDs.Tables[i].Columns)  
                headerRow.CreateCell(column.Ordinal).SetCellValue(column.ColumnName);  
            // handling value.             
            int rowIndex = 1;  
            foreach (DataRow row in sourceDs.Tables[i].Rows)  
            {  
                HSSFRow dataRow = (HSSFRow)sheet.CreateRow(rowIndex);  
                foreach (DataColumn column in sourceDs.Tables[i].Columns)  
                {  
                    dataRow.CreateCell(column.Ordinal).SetCellValue(row[column].ToString());  
                }  
                rowIndex++;  
            }  
        }  
        workbook.Write(ms);  
        ms.Flush();  
        ms.Position = 0;  
        workbook = null;  
        return ms;  
    }  
    /// <summary>  
    /// 由DataSet导出Excel  
    /// </summary>    
    /// <param name="sourceTable">要导出数据的DataTable</param>  
    /// <param name="fileName">指定Excel工作表名称</param>  
    /// <returns>Excel工作表</returns>     
    public static void ExportDataSetToExcel(DataSet sourceDs, string fileName)  
    {  
        //检查是否有Table数量超过65325  
        for (int t = 0; t < sourceDs.Tables.Count; t++)  
        {  
            if (sourceDs.Tables[t].Rows.Count > ExcelMaxRow)  
            {  
                DataSet ds = GetdtGroup(sourceDs.Tables[t].Copy());  
                sourceDs.Tables.RemoveAt(t);  
                //将得到的ds插入 sourceDs中  
                for (int g = 0; g < ds.Tables.Count; g++)  
                {  
                    DataTable dt = ds.Tables[g].Copy();  
                    sourceDs.Tables.Add(dt);  
                }  
                t--;  
            }  
        }  
   
        MemoryStream ms = ExportDataSetToExcel(sourceDs) as MemoryStream;  
        HttpContext.Current.Response.AppendHeader("Content-Disposition""attachment;filename=" + fileName);  
        HttpContext.Current.Response.BinaryWrite(ms.ToArray());  
        HttpContext.Current.ApplicationInstance.CompleteRequest();  
        //HttpContext.Current.Response.End();  
        ms.Close();  
        ms = null;  
    }  
    /// <summary>  
    /// 由DataTable导出Excel  
    /// </summary>  
    /// <param name="sourceTable">要导出数据的DataTable</param>  
    /// <returns>Excel工作表</returns>     
    private static Stream ExportDataTableToExcel(DataTable sourceTable)  
    {  
        HSSFWorkbook workbook = new HSSFWorkbook();  
        MemoryStream ms = new MemoryStream();  
        HSSFSheet sheet = (HSSFSheet)workbook.CreateSheet(sourceTable.TableName);  
        HSSFRow headerRow = (HSSFRow)sheet.CreateRow(0);  
        // handling header.       
        foreach (DataColumn column in sourceTable.Columns)  
            headerRow.CreateCell(column.Ordinal).SetCellValue(column.ColumnName);  
        // handling value.       
        int rowIndex = 1;  
        foreach (DataRow row in sourceTable.Rows)  
        {  
            HSSFRow dataRow = (HSSFRow)sheet.CreateRow(rowIndex);  
            foreach (DataColumn column in sourceTable.Columns)  
            {  
                dataRow.CreateCell(column.Ordinal).SetCellValue(row[column].ToString());  
            }  
            rowIndex++;  
        }  
        workbook.Write(ms);  
        ms.Flush();  
        ms.Position = 0;  
        sheet = null;  
        headerRow = null;  
        workbook = null;  
        return ms;  
    }  
    /// <summary>  
    /// 由DataTable导出Excel  
    /// </summary>  
    /// <param name="sourceTable">要导出数据的DataTable</param>  
    /// <param name="fileName">指定Excel工作表名称</param>  
    /// <returns>Excel工作表</returns>  
    public static void ExportDataTableToExcel(DataTable sourceTable, string fileName)  
    {  
        //如数据超过65325则分成多个Table导出  
        if (sourceTable.Rows.Count > ExcelMaxRow)  
        {  
            DataSet ds = GetdtGroup(sourceTable);  
            //导出DataSet  
            ExportDataSetToExcel(ds, fileName);  
        }  
        else 
        {  
            MemoryStream ms = ExportDataTableToExcel(sourceTable) as MemoryStream;  
            HttpContext.Current.Response.AppendHeader("Content-Disposition""attachment;filename=" + fileName);  
            HttpContext.Current.Response.BinaryWrite(ms.ToArray());  
            HttpContext.Current.ApplicationInstance.CompleteRequest();  
            //HttpContext.Current.Response.End();  
            ms.Close();  
            ms = null;  
        }  
    }  
   
    /// <summary>  
    /// 传入行数超过65325的Table,返回DataSet  
    /// </summary>  
    /// <param name="dt"></param>  
    /// <returns></returns>  
    public static DataSet GetdtGroup(DataTable dt)  
    {  
        string tablename = dt.TableName;  
   
        DataSet ds = new DataSet();  
        ds.Tables.Add(dt);  
   
        double n = dt.Rows.Count / Convert.ToDouble(ExcelMaxRow);  
   
        //创建表  
        for (int i = 1; i < n; i++)  
        {  
            DataTable dtAdd = dt.Clone();  
            dtAdd.TableName = tablename + "_" + i.ToString();  
            ds.Tables.Add(dtAdd);  
        }  
   
        //分解数据  
        for (int i = 1; i < ds.Tables.Count; i++)  
        {  
            //新表行数达到*** 或 基表数量不足  
            while (ds.Tables[i].Rows.Count != ExcelMaxRow && ds.Tables[0].Rows.Count != ExcelMaxRow)  
            {  
                ds.Tables[i].Rows.Add(ds.Tables[0].Rows[ExcelMaxRow].ItemArray);  
                ds.Tables[0].Rows.RemoveAt(ExcelMaxRow);  
   
            }  
        }  
   
        return ds;  
    }  
   
    /// <summary>  
    /// 由DataTable导出Excel  
    /// </summary>  
    /// <param name="sourceTable">要导出数据的DataTable</param>  
    /// <param name="fileName">指定Excel工作表名称</param>  
    /// <returns>Excel工作表</returns>  
    public static void ExportDataTableToExcelModel(DataTable sourceTable, string modelpath, string modelName, string fileName, string sheetName)  
    {  
        int rowIndex = 2;//从第二行开始,因为前两行是模板里面的内容  
        int colIndex = 0;  
        FileStream file = new FileStream(modelpath + modelName + ".xls", FileMode.Open, FileAccess.Read);//读入excel模板  
        HSSFWorkbook hssfworkbook = new HSSFWorkbook(file);  
        HSSFSheet sheet1 = (HSSFSheet)hssfworkbook.GetSheet("Sheet1");  
        sheet1.GetRow(0).GetCell(0).SetCellValue("excelTitle");      //设置表头  
        foreach (DataRow row in sourceTable.Rows)  
        {   //双循环写入sourceTable中的数据  
            rowIndex++;  
            colIndex = 0;  
            HSSFRow xlsrow = (HSSFRow)sheet1.CreateRow(rowIndex);  
            foreach (DataColumn col in sourceTable.Columns)  
            {  
                xlsrow.CreateCell(colIndex).SetCellValue(row[col.ColumnName].ToString());  
                colIndex++;  
            }  
        }  
        sheet1.ForceFormulaRecalculation = true;  
        FileStream fileS = new FileStream(modelpath + fileName + ".xls", FileMode.Create);//保存  
        hssfworkbook.Write(fileS);  
        fileS.Close();  
        file.Close();  
    }  

  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
  • 14.
  • 15.
  • 16.
  • 17.
  • 18.
  • 19.
  • 20.
  • 21.
  • 22.
  • 23.
  • 24.
  • 25.
  • 26.
  • 27.
  • 28.
  • 29.
  • 30.
  • 31.
  • 32.
  • 33.
  • 34.
  • 35.
  • 36.
  • 37.
  • 38.
  • 39.
  • 40.
  • 41.
  • 42.
  • 43.
  • 44.
  • 45.
  • 46.
  • 47.
  • 48.
  • 49.
  • 50.
  • 51.
  • 52.
  • 53.
  • 54.
  • 55.
  • 56.
  • 57.
  • 58.
  • 59.
  • 60.
  • 61.
  • 62.
  • 63.
  • 64.
  • 65.
  • 66.
  • 67.
  • 68.
  • 69.
  • 70.
  • 71.
  • 72.
  • 73.
  • 74.
  • 75.
  • 76.
  • 77.
  • 78.
  • 79.
  • 80.
  • 81.
  • 82.
  • 83.
  • 84.
  • 85.
  • 86.
  • 87.
  • 88.
  • 89.
  • 90.
  • 91.
  • 92.
  • 93.
  • 94.
  • 95.
  • 96.
  • 97.
  • 98.
  • 99.
  • 100.
  • 101.
  • 102.
  • 103.
  • 104.
  • 105.
  • 106.
  • 107.
  • 108.
  • 109.
  • 110.
  • 111.
  • 112.
  • 113.
  • 114.
  • 115.
  • 116.
  • 117.
  • 118.
  • 119.
  • 120.
  • 121.
  • 122.
  • 123.
  • 124.
  • 125.
  • 126.
  • 127.
  • 128.
  • 129.
  • 130.
  • 131.
  • 132.
  • 133.
  • 134.
  • 135.
  • 136.
  • 137.
  • 138.
  • 139.
  • 140.
  • 141.
  • 142.
  • 143.
  • 144.
  • 145.
  • 146.
  • 147.
  • 148.
  • 149.
  • 150.
  • 151.
  • 152.
  • 153.
  • 154.
  • 155.
  • 156.
  • 157.
  • 158.
  • 159.
  • 160.
  • 161.
  • 162.
  • 163.
  • 164.
  • 165.
  • 166.
  • 167.
  • 168.
  • 169.
  • 170.
  • 171.
  • 172.
  • 173.
  • 174.
  • 175.
  • 176.
  • 177.
  • 178.
  • 179.
  • 180.
  • 181.
  • 182.
  • 183.
  • 184.
  • 185.
  • 186.
  • 187.
  • 188.
  • 189.
  • 190.
  • 191.
  • 192.
  • 193.
  • 194.
  • 195.
  • 196.
  • 197.
  • 198.
  • 199.
  • 200.
  • 201.
  • 202.
  • 203.
  • 204.
  • 205.
  • 206.
  • 207.
  • 208.
  • 209.
  • 210.
  • 211.
  • 212.
  • 213.
  • 214.

Config配置了 【ExcelMaxRow】值 65535

原文链接:http://www.cnblogs.com/Tsong/archive/2013/02/21/2920941.html

责任编辑:林师授 来源: 博客园
相关推荐

2009-08-31 09:19:31

c#隐藏窗口

2009-08-25 17:31:57

C#读取文件

2009-09-24 14:59:38

C#编写COM组件

2009-09-01 18:35:53

C#判断文件存在

2009-08-03 11:37:36

C#日期时间控件

2009-08-13 10:40:15

C#读取Excel

2009-08-13 10:15:50

C#读取Excel

2010-01-22 14:46:25

C++语言

2009-08-03 17:53:11

XML数据

2009-08-18 16:14:05

C# 操作Excel

2009-08-13 10:27:28

C#读取Excel数据

2009-09-14 18:11:23

C#排序方法

2009-07-30 15:57:30

C#时间

2024-08-23 09:00:18

开发跨域请求

2009-08-05 13:34:18

C#日期相减

2009-08-06 17:24:08

C#字符串

2009-08-25 14:59:36

ASP.NET和C#连

2009-08-06 16:36:20

研究C#和.Net

2009-09-02 17:07:06

C#数组操作

2009-08-07 12:57:03

C#读取Excel
点赞
收藏

51CTO技术栈公众号