引言
Microsoft Excel是微软公司的办公软件Microsoft office的组件之一,是由Microsoft为Windows和Apple Macintosh操作系统的电脑而编写和运行的一款试算表软件。Excel 是微软办公套装软件的一个重要的组成部分,它可以进行各种数据的处理、统计分析和辅助决策操作,广泛地应用于管理、统计财经、金融等众多领域。它使用的灵活性使我们出报表等工作时不由自主的想到使用Excel。然而我们在C#中如何操作Excel表呢?结下来给大家介绍一下如何往Excel模板中写入数据。再正式进入案例之前,写简要说说一些常识。
Excel对象
微软的Excel对象模型包括了128个不同的对象,从矩形,文本框等简单的对象到透视表,图表等复杂的对象.下面我们简单介绍一下其中最重要,也是用得最多的四个对象。
(1) Application对象。Application对象处于Excel对象层次结构的顶层,表示Excel自身的运行环境。
(2) Workbook对象。Workbook对象直接地处于Application对象的下层,表示一个Excel工作薄文件。
(3) Worksheet对象。Worksheet对象包含于Workbook对象,表示一个Excel工作表。
(4) Range对象。Range对象包含于Worksheet对象,表示Excel工作表中的一个或多个单元格。
C#中的受管代码和非受管代码
在.net公用语言框架内运行的程序为受管代码。受管代码在程序中所有类型都受到严格检查,没有指针,对内存的管理完全由运行系统控制。受控状态下,编写程序更为容易,且更少出错,我们可以花更多的时间在解决实际问题上而不是在计算机语言问题上。相对而言,那些在.NET框架外运行的程序为非受管代码。比如:COM组件、ActiveX组件、Win32 API函数、指针运算等。C#编程中在某些特定情况下,需要运用非受管代码,例如,要利用一个成熟的COM组件,或者调用一个API函数,或者用指针去编写实时/高效程序等。
Visual C#中调用Excel的COM组件
一个.NET组件事实上是一个.NET下的DLL,它包含的不仅是运行程序本身,更重要的是包含这个DLL的描述信息(Meta Data,即元数据),而一个COM组件是用其类库(TLB)储存其描述信息。这些COM组件都是非受管代码,要在Visual C#中使用这些非受管代码的COM组件,就必须把他们转换成受管代码的.NET组件。所以在用Visual C#调用Excel表格之前,必须完成从COM组件的非受管代码到受管代码的类库的转换。
1、将Excel的COM组件转换为.NET组件
在项目中打开Add Reference对话框,选择COM栏,之后在COM列表中找到"Microsoft Excel 12.0 Object Library"(Office 2003),然后将其加入到项目的References中即可。Visual C#.NET会自动产生相应的.NET组件文件,以后即可正常使用。
这个转换形成.NET组件不能单独使用,它不过是以前的COM组件的一个外层包装,在.NET中可以通过这个外层包装去发现原来的COM组件并调用其相应的界面函数。所以它必须与原来的COM组件一起起作用。
2、Visual C#打开Excel表格
事实上,在C#中使用一个经转换的COM组件和使用任何一个其它.NET组件完全一样。可以用new关键字创建一个经转换的COM组件,然后再像使用任何一个其它C#对象一样使用这个组件对象。
在转换后的.NET组件中定义了一个命名空间Excel,在此命名空间中封装了一个类Application,这个类和启动Excel表格有非常重要的关系,在Visual C#中,只需要下列三行代码就可以完成打开Excel表格的工作,具体如下:
Excel.Application excel = new Excel.Application ();//引用Excel对象
excel.Workbooks.Add(ExcelTemplate);//ExcelTemplate的值为Boolean值的true,则新建一个工作簿,如果是Excel模板的路径,这按照该模板新建一个工作簿。
但此时的Excel表格是一个空的表格,没有任何内容,下面就来介绍如何往Excel表格中输入数据。
3、往Excel表格中输入数据
在命名空间"Excel"中,还定义了一个类"Cell",这个类所代表的就是Excel表格中的一个单元格。通过给"Cell"赋值,从而实现往Excel表格中输入相应的数据,下列代码功能是打开Excel表格,并且往表格输入一些数据。
Cells[RowIndex, ColummnIndex] = Value;
4、使用实例,该实例主要是用于封装操作Excel的类。主要用于打开相关的Excel模板然后往模板中写入数据。
必须添加引用,对引用进行了重命名:
using Excel = Microsoft.Office.Interop.Excel;
数据调用方法:
private void DoToExcel(HtmlDocument doc)
{
DoExcel excel = new DoExcel(Application.StartupPath + @"\DataTemplate.xls", "Data");
//表头,如果是合并单元格的话,写入合并单元的左上角的单元格号,即可。
excel.SetCellsValue(1, 1, "测试实验报告");
excel.SaveAs("测量测验报告");
excel.Dispose();
MessageBox.Show("导出Excel完成");
}
操作Excel类:
public class DoExcel
{
///
/// Excel对象
///
Excel.Application excel = null;
Excel.Worksheet worksheet = null;
///
/// 创建一个新的Excel操作类
///
/// Excel模板,输入模板的地址;如果没有模板就填入则输入"True"作为参数,新建一个无模板的工作簿
/// 可以指定要操作的sheet表名称,如果新建的时候输入参数 null ,表示当前工作表
public DoExcel(string ExcelTemplate, string WorksheetName)
{
//创建Excel对象
excel = new Excel.ApplicationClass();
excel.Visible = false;//使Excel可视
//获取Excel模板
Excel.Workbook workBook = excel.Workbooks.Add(ExcelTemplate);
if (WorksheetName == null || ExcelTemplate != null && ExcelTemplate.ToLower().Equals("true"))
{
worksheet = workBook.ActiveSheet as Excel.Worksheet;
}
else
{
worksheet = workBook.Worksheets.get_Item(WorksheetName) as Excel.Worksheet;
}
}
///
/// 设置数据
///
/// 行号
/// 列号
/// 值
public void SetCellsValue(object RowIndex, object ColummnIndex, string Value)
{
worksheet.Cells[RowIndex, ColummnIndex] = Value;
}
///
/// 保存Excel
///
public void SaveAs()//string ExcelFileName
{
SaveFileDialog dialog = new SaveFileDialog();
dialog.Filter = "Excel 97-2003(*.xls)|*.xls";
if (dialog.ShowDialog() == DialogResult.OK)
{
worksheet.SaveAs(dialog.FileName, Excel.XlFileFormat.xlExcel8, null, null, null, null, null, null, null, null);
}
}
///
/// 保存Excel
///
public void SaveAs(string FileName)
{
SaveFileDialog dialog = new SaveFileDialog();
dialog.Filter = "Excel 97-2003(*.xls)|*.xls";
dialog.FileName = FileName;
if (dialog.ShowDialog()== DialogResult.OK)
{
if (File.Exists(dialog.FileName))
{
File.Delete(dialog.FileName);
}
worksheet.SaveAs(dialog.FileName, Excel.XlFileFormat.xlExcel8, null, null, null, null, null, null, null, null);
}
}
public void Dispose()
{
worksheet = null;
excel.Workbooks.Close();
excel.Quit();
}
}
注意事项:我在使用过程中出现了如下异常:无法嵌入互操作类型“Microsoft.Office.Interop.Excel.ApplicationClass”。请改用适用的接口。
解决办法是将引用的DLL:Microsoft.Office.Interop.Excel;的嵌入互操作类型改为false,就可以了。
5、安装一个使用COM组件的.net程序
如果要将这样的程序安装运行在另一台机器上,那么除了安装运行程序外,还做三件事。
首先,是安装.NET运行系统。因为任何一个.NET程序都不能离开.NET运行系统去独立运行。
其次,所调用的COM组件必须要安装在目标机器上。本例中大多数目标机器上都装有Microsoft Office的Excel,一般不会有这个问题。但如果是另一个用户自定义的COM组件,那么这个COM组件在运行.NET程序之前必须先安装好。
最后,转换后的.NET组件DLL文件要安装在目标机器上。因为.NET组件不需要在Windows ReGIStry中注册,所以最简单的方法是将.NET组件DLL文件拷贝到运行程序目录下。如果此.NET组件被多个.NET程序共享,可以将其安装在.NET公用组件区中,从而可被任何一个.NET组件使用。只有当一个.NET组件参与了事务处理时,才需要将它注册为一个COM+组件。因为.NET仍然用传统的COM+机制来处理事务的提交、回滚等。
小结
通过以上讨论,我们知道了在C#中,如何使用Excel的COM组件。如果只是为了读取Excel表中的数据我们可以通过OLEDB来操作。当作文件数据源来操作。