再现C#导出Excel源码

网上反应比较强烈。本人也因为工作需要的原因,将其封装了成了ExcelManager。企业当中,做报表的数据来源肯定就是数据库了。该ExcelManager目前只提供Ms Sql Server的支持,因为我们公司使用的就是ms sql server 2000 了。封装后的ExcelManager,你只需传入你的报表表头(一级表头、二级表头。大部分有两级也就够了。如果你有多个,可自行修改该类.),并将对应的数据库表字段传入类库中的方法DeclareExcelApp即可。
同前一篇一样,你可将下面代码复制另存一个新类就可以了(不知为什么,我在家里上网老是传附件不上来!faint...)。随后,我会给出一个调用的方法的:
namespace  ExportToExcel
{
    
using  System;
    
using  System.Data;
    
using  System.Data.SqlClient;
    
using  System.Windows.Forms;
    
using  System.Runtime.InteropServices;

    
/* **********************************************************************************
     ****Class Name :   ExcelManger
     ****Author:            KingNa
     ****Create Date :   2006-9-1
     ****CopyRight:     Reserve this info if you want to User this Class
    **********************************************************************************
*/
    
public   class  ExcelManager:IDisposable
    {
        Excel.Range m_objRange 
=   null ;
        Excel.Application m_objExcel 
=   null ;
        Excel.Workbooks m_objBooks 
=   null ;
        Excel._Workbook m_objBook 
=   null ;
        Excel.Sheets m_objSheets 
=   null ;
        Excel._Worksheet m_objSheet 
=   null ;
        Excel.QueryTable m_objQryTable 
=   null ;
        
object  m_objOpt  =  System.Reflection.Missing.Value;
        
// DataBase-used variable
         private  System.Data.SqlClient.SqlConnection sqlConn  =   null ;
        
private   string  strConnect  =   string .Empty;
        
private  System.Data.SqlClient.SqlCommand sqlCmd  =   null ;

        
// Sheets variable
         private   double  dbSheetSize  =   65535 ; // the hight limit number in one sheet
         private   int  intSheetTotalSize  =   0 ; // total record can divied sheet number
         private   double  dbTotalSize  =   0 ; // record total number


        
///   <summary>
        
///  建构函数
        
///   </summary>
         public  ExcelManager(){}

        
///   <summary>
        
///  建构函数
        
///   </summary>
        
///   <param name="dbHL"> 一个Excel表格的最大记录数 </param>
        
///   <param name="dbTotal"> 该数据库表共查询出多少条记录 </param>
        
///   <param name="intDivide"> 查询出的记录可分成几个Excel </param>
        
///   <param name="conn"> sqlConnection </param>
         public  ExcelManager(Double dbHL,Double dbTotal, int  intDivide,SqlConnection conn )
        {
            dbSheetSize 
=  dbHL;
            intSheetTotalSize 
=  intDivide;
            dbTotalSize 
=  dbTotal;
            sqlConn 
=  conn;
        }
        
///   <summary>
        
///  建构函数
        
///   </summary>
        
///   <param name="dbHL"> 一个Excel表格的最大记录数 </param>
        
///   <param name="strTableName"> 需查询的数据库的表名 </param>
        
///   <param name="conn"> sqlConnection </param>
         public  ExcelManager(Double dbHL, string  strTableName,SqlConnection conn)
        {
            dbSheetSize 
=  dbHL;
            sqlConn 
=  conn;
            intSheetTotalSize 
=  GetTotalSize(strTableName,sqlConn);
        }

        
public   void  Dispose()
        {
            Dispose(
true );
            GC.SuppressFinalize(
this );
        }
        
private   void  Dispose( bool  disposing)
        {
            
if (disposing)
            {
                
//  Dispose managed resources.
                Marshal.FinalReleaseComObject(m_objExcel);
                m_objRange 
=   null ;
                m_objSheet 
=   null ;
                m_objSheets 
=   null ;
                m_objBooks 
=   null ;
                m_objBook 
=   null ;
                m_objExcel 
=   null ;
            }
        }
        
///   <summary>
        
///  取得总记录数跟可分成几个Excel sheet.
        
///   </summary>
        
///   <param name="strTableName"> 被查询的数据库的表名 </param>
        
///   <param name="sqlConn"> sqlConnection </param>
        
///   <returns> 可分成Excel Sheet的个数 </returns>
         private   int  GetTotalSize( string  strTableName,SqlConnection sqlConn)
        {
            
// sqlConn = new System.Data.SqlClient.SqlConnection(strConnect);
            sqlCmd  =   new  System.Data.SqlClient.SqlCommand( " Select Count(*) From  " + strTableName, sqlConn);
            
if ( this .sqlConn.State  ==  ConnectionState.Closed) sqlConn.Open();
            dbTotalSize 
=  ( int )sqlCmd.ExecuteScalar();
            sqlConn.Close();
            
return  ( int )Math.Ceiling(dbTotalSize  /   this .dbSheetSize);
        }

        
///   <summary>
        
///  新建一个Excel实例
        
///   </summary>
        
///   <param name="strTitle"> Excel表头上的文字 </param>
         public   void  DeclareExcelApp( string [] strTitle, string  strSql, string  strTableName, string  strMastTitle)
        {
            m_objExcel 
=   new  Excel.ApplicationClass();
            m_objExcel.Visible 
=   true ;
            m_objBooks 
=  (Excel.Workbooks)m_objExcel.Workbooks;
            m_objBook 
=  (Excel._Workbook)(m_objBooks.Add(m_objOpt));
            m_objSheets 
=  (Excel.Sheets)m_objBook.Worksheets;
            
if  (intSheetTotalSize  <=   3 )
            {
                
if  ( this .dbTotalSize  <=   this .dbSheetSize)
                {
                    
this .ExportDataByQueryTable( 1 false ,strTitle,strSql,strTableName,strMastTitle );
                    
return ;
                }
                
else   if  ( this .dbTotalSize  <=   this .dbSheetSize  *   2 )
                {
                    
this .ExportDataByQueryTable( 1 false ,strTitle,strSql,strTableName,strMastTitle );
                    
this .ExportDataByQueryTable( 2 true ,strTitle,strSql,strTableName,strMastTitle );
                    
return ;
                }
                
else
                {
                    
this .ExportDataByQueryTable( 1 false ,strTitle,strSql,strTableName,strMastTitle );
                    
this .ExportDataByQueryTable( 2 true ,strTitle,strSql,strTableName,strMastTitle );
                    
this .ExportDataByQueryTable( 3 true ,strTitle,strSql,strTableName,strMastTitle );
                    
return ;
                }
            }
            
for  ( int  i  =   3 ; i  <  intSheetTotalSize; i ++ )
            {
                m_objSheets.Add(m_objOpt, m_objSheets.get_Item(i), m_objOpt, m_objOpt);
            }
            ExportDataByQueryTable(
1 false ,strTitle,strSql,strTableName,strMastTitle );
            
for  ( int  i  =   2 ; i  <=  m_objSheets.Count; i ++ )
            {
                ExportDataByQueryTable(i, 
true ,strTitle,strSql,strTableName,strMastTitle );
            }
        }
        
///   <summary>
        
///  以用户输入的文件名保存文件
        
///   </summary>
         public   void  SaveExcelApp()
        {
            
string  excelFileName  =   string .Empty;
            SaveFileDialog sf 
=   new  SaveFileDialog();
            sf.Filter 
=   " *.xls|*.* " ;
            
if  (sf.ShowDialog()  ==  DialogResult.OK)
            {
                excelFileName 
=  sf.FileName;
            }
            
else
            {
                
return ;
            }
            m_objBook.SaveAs(excelFileName, m_objOpt, m_objOpt, m_objOpt, m_objOpt, m_objOpt, 
                Excel.XlSaveAsAccessMode.xlNoChange, m_objOpt, m_objOpt, m_objOpt, m_objOpt,m_objOpt);
            
if  (m_objExcel  !=   null )
                m_objExcel 
=   null ;
        }
        
///   <summary>
        
///  利用Excel的QueryTable导出数据
        
///   </summary>
        
///   <param name="intSheetNumber"> 导出第几个sheet </param>
        
///   <param name="blIsMoreThan"> 余下的数据是否大于指定的每个Sheet的最大记录数 </param>
        
///   <param name="strTitle"> 表头,需与查询sql语句对齐一致。 </param>
        
///   <param name="strSql"> 查询的sql语句,表头的文字需与该sql语句对齐一致。 </param>
        
///   <param name="strTablName"> 查询的表名 </param>     
        
///   <param name="strMastTitle"> 主标题 </param>
        
///   </summary>
         public   void  ExportDataByQueryTable( int  intSheetNumber,  bool  blIsMoreThan, string [] strTitle, string  strSql, string  strTablName, string  strMastTitle)
        {
            
string  strQuery  =   string .Empty;
            
if  (blIsMoreThan)
            {
                strQuery 
=   " Select Top  "   +
                    
this .dbSheetSize  +  strSql  +   "   From  "   +  strTablName  +   "  Where Not  OrderID In (Select Top  "   +
                    dbSheetSize 
*  (intSheetNumber  -   1 +   "   OrderID From  "   +  strTablName  +   " ) " ;
            }
            
else
            {
                strQuery 
=   " Select Top  "   +   this .dbSheetSize  +  strSql +   "   From  " + strTablName;

            }
            m_objSheet 
=  (Excel._Worksheet)(m_objSheets.get_Item(intSheetNumber));

            m_objSheet.Cells[
1 , 1 =  strMastTitle;
            m_objSheet.Cells[
2 , 1 =   " 打印日期 " + DateTime.Now.ToShortDateString();
            
for ( int  i  =   1 ;i <= strTitle.Length;i ++ )
            {
                m_objSheet.Cells[
4 ,i]  =  strTitle[i - 1 ].ToString();
            }
            m_objRange 
=  m_objSheet.get_Range( " A5 " , m_objOpt);
            m_objQryTable 
=  m_objSheet.QueryTables.Add( " OLEDB;Provider=SQLOLEDB.1; "   +  sqlConn.ConnectionString, m_objRange, strQuery);
            m_objQryTable.RefreshStyle 
=  Excel.XlCellInsertionMode.xlInsertEntireRows;
            m_objQryTable.FieldNames 
=   false ;
            m_objQryTable.Refresh(
false );
        }
    }
}

全盘复制另存新类后,调用方法示例如下:
         private   void  button2_Click( object  sender, EventArgs e)
        {
            
#region  ExcelManager封装类导出Excel
            String strConnet 
= " Data Source='localhost';Password = ;User ID=sa;Initial Catalog=Northwind " ;
            System.Data.SqlClient.SqlConnection sqlConn 
=
                
new  System.Data.SqlClient.SqlConnection(strConnet);
            ExcelManager exc 
=   new  ExcelManager( 65530 " Orders " , sqlConn);
            
try
            {
                exc.DeclareExcelApp(
new   string [] {  " 编号 " , " 供应商编号 "  },  "  OrderID,CustomerID  " " Orders " " 报表标题 " );
                
// exc.SaveExcelApp();
            }
            
catch (Exception E)
            {
                MessageBox.Show(E.ToString());
            }
            
finally
            {
                exc.Dispose();
            }
            
#endregion
        } 

以上使用的是Excel 2002 英文版。2003有些方法稍有出入。可参照前篇的C#导出Excel源码。另外,如果可能的话,我将封装其它数据库类型的Excel导出。有兴趣的朋友,请继续关继!
 
  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值