题 从C#创建Excel(.XLS和.XLSX)文件


如何使用C#创建Excel电子表格而无需在运行代码的计算机上安装Excel?


1571


起源


不确定这是否是正确的地方,但看看ClosedXML。它确实对你的代码设置了> 2003限制,但到目前为止,我们已经非常成功地使用了它。 - Carl
这可以通过.NET Framework完成,如上所述 这里或者像某些图书馆那样容易得多 GemBox.Spreadsheet。 - NixonUposseen


答案:


您可以使用名为ExcelLibrary的库。这是一个免费的开源库,发布在Google Code上:

ExcelLibrary

这看起来是您上面提到的PHP ExcelWriter的一个端口。它还不会写入新的.xlsx格式,但他们正在努力添加该功能。

它非常简单,小巧且易于使用。此外,它还有一个DataSetHelper,可让您使用DataSet和DataTable轻松处理Excel数据。

ExcelLibrary似乎仍然只适用于较旧的Excel格式(.xls文件),但可能会在以后为较新的2007/2010格式添加支持。

你也可以使用 EPPlus,仅适用于Excel 2007/2010格式文件(.xlsx文件)。

如评论中所述,每个库都有一些已知的错误。总之,随着时间的推移,EPPlus似乎是最好的选择。它似乎也更积极地更新和记录。

此外,如下面的@АртёмЦарионов所述,EPPlus支持数据透视表,ExcelLibrary可能会有一些支持(ExcelLibrary中的数据透视表问题

这里有几个链接供快速参考:
ExcelLibrary  - GNU较小的GPL
EPPlus  - GNU较宽松通用公共许可证(LGPL)

这里是ExcelLibrary的一些示例代码:

以下是从数据库获取数据并从中创建工作簿的示例。请注意,ExcelLibrary代码是底部的单行:

//Create the data set and table
DataSet ds = new DataSet("New_DataSet");
DataTable dt = new DataTable("New_DataTable");

//Set the locale for each
ds.Locale = System.Threading.Thread.CurrentThread.CurrentCulture;
dt.Locale = System.Threading.Thread.CurrentThread.CurrentCulture;

//Open a DB connection (in this example with OleDB)
OleDbConnection con = new OleDbConnection(dbConnectionString);
con.Open();

//Create a query and fill the data table with the data from the DB
string sql = "SELECT Whatever FROM MyDBTable;";
OleDbCommand cmd = new OleDbCommand(sql, con);
OleDbDataAdapter adptr = new OleDbDataAdapter();

adptr.SelectCommand = cmd;
adptr.Fill(dt);
con.Close();

//Add the table to the data set
ds.Tables.Add(dt);

//Here's the easy part. Create the Excel worksheet from the data set
ExcelLibrary.DataSetHelper.CreateWorkbook("MyExcelFile.xls", ds);

创建Excel文件就像这样简单。您也可以手动创建Excel文件,但上述功能给我留下了深刻的印象。


877



ExcelLibrary已被特殊的EPPlus取代 - epplus.codeplex.com。 Jan定期更新。一直在使用它,它是我们合作过的最好的开源项目之一。 - Mark A
不。使用EppPlus - epplus.codeplex.com。这是最新的。支持格式化。我用它。 - Bill Paetzke
似乎ExcelLibrary仅支持.xls和EPPlus .xlsx,因此它们相互补充。 - jmster
-1如果您要发布示例代码,您也可以确保它是正确的。 使用此接口的Dispose方法与垃圾收集器一起显式释放非托管资源。当不再需要该对象时,对象的使用者可以调用此方法。 - ta.speot.is
请停止提出EPPlus作为ExcelLibrary的替代方案,直到它具有相同的功能(一个处理XLS,另一个处理XLSX)。尽管我喜欢EPPlus,但它根本不是OP需求(XLS)的答案。 - Chris Rogers


如果您对xlsx格式感到满意,请尝试我的 CodePlex网站 GitHub项目。 EPPlus。从ExcelPackage的源代码开始,但今天它完全重写。 支持范围,单元格样式,图表,形状,图片,名称范围,自动过滤器和许多其他东西。


491



我完全免费的库还允许您使用Open XML将任何DataSet,DataTable或List <>直接导出到Excel 2007 .xlsx文件中。完整源代码和演示,可在此处获得: mikesknowledgebase.com/pages/CSharp/ExportToExcel.htm - Mike Gledhill
许可证现在是LGPL,发布说明如下: epplus.codeplex.com/releases/view/79802 - Simon D
这些例子很有帮助。我能够在几个小时内将我的代码从使用Microsoft互操作库(非常慢)更改为此库(版本4.x)。我的基准测试使用两个选项卡和大约750,000个单元格写入文件。使用MS interop需要13分钟。使用EPPlus需要10秒,大约80倍的加速。很高兴! - Paul Chernoch
@JanKällman您应该更新CodePlex页面,以显示您已获得以下方法: LoadFromCollection<T>, LoadFromDataTable 等(通过发现 这里) - PeterX
为了清楚起见,LGPL允许软件链接到没有GPL的感染部分。您只需要对ClosedXml进行开源更改,或者如果直接将源代码(而不是引用ClosedXml程序集)放在应用程序内部,则需要打开应用程序源代码。 - Chris Marisic


我成功地使用了以下开源项目:

  • 用于OOXML格式的ExcelPackage(Office 2007)

  • NPOI for .XLS格式(Office 2003)。 NPOI 2.0 (Alpha)也支持XLSX。

看看我的博文:

在C#中创建Excel电子表格.XLS和.XLSX

NPOI与Excel表和动态图表


147



关于NPOI的注释 - 行和列引用是从零开始的。适用于填充现有模板。 - John M
NPOI 2现在处于测试阶段,我在我的项目中使用它来进行简单的导出而没有任何问题。 - Travis
有用。它还有一些有史以来发明的最恶劣的类和名称空间名称 - 模仿基础数据格式的恶劣而不是模仿它。 - Roman Starkov
这个问题及其答案真的很古老。 NPOI现在是要走的路,我希望在我浪费时间与EPPlus和ExcelLibrary尝试获得适用于.xls和.xlsx的解决方案之前,这个答案是最重要的。从中获取C#下载 npoi.codeplex.com。我发现的最好的文档,即使它是Java版本 poi.apache.org - SurfingSanta
NPOI已从Codeplex迁移到 Github上。 - jerhewet


那么使用Open XML SDK 2.0 for Microsoft Office呢?

一些好处:

  • 不需要安装Office
  • 由Microsoft制作=体面的MSDN文档
  • 只需一个.Net dll即可在项目中使用
  • SDK附带了许多工具,如diff,validator等

链接:


141



需要注意的是,这个DLL只有5 MB以上,并且仅限于Office 2007格式。但肯定是对我有用的最简单,最快速的解决方案。 - Josh Brown
只是提前v2.5已经出来并且可以下载 这里。 - Snuffleupagus
SDK将XML建模为类,以便将每个XML标记映射到标记,然后您必须正确构建类层次结构(每个实例都有一个子实例/标记的集合)。这意味着您必须知道Excel文件的XML结构,这非常复杂。使用如上所述的EPPlus之类的包装器会更容易,这简化了事情。 - Tsahi Asher
可以在以下位置找到Microsoft Open XML SDK的一个很好的示例 - Open XML Writer polymathprogrammer.com/2012/08/06/...  或者参见Stack Overflow解决方案 stackoverflow.com/questions/11370672/... - Greg
我发现Microsoft Open XML SDK的Open XML Writer非常棒。使用上面的解决方案(特别是Vincent Tom的样本(Poly Math)),可以很容易地构建一个通过大量数据流进行编写的编写器,并以类似的方式编写记录,而不是为您所做的事情复杂化CSV;但是你正在写xml。 Open XML是Microsoft认为它是新的Office格式的思维模式。如果您想要查看XML内容,可以随时将它们从.xslx重命名为.zip文件。 - Greg


您可以使用OLEDB来创建和操作Excel文件。检查一下: 使用OLEDB读取和写入Excel

典型例子:

using (OleDbConnection conn = new OleDbConnection("Provider=Microsoft.Jet.OLEDB.4.0;Data Source=C:\\temp\\test.xls;Extended Properties='Excel 8.0;HDR=Yes'"))
{
  conn.Open();
  OleDbCommand cmd = new OleDbCommand("CREATE TABLE [Sheet1] ([Column1] string, [Column2] string)", conn);
  cmd.ExecuteNonQuery();
}

编辑 - 更多链接:


95



在x64中运行时,有人可以确认这是否有效吗?我非常确定Jet只有在你的应用程序是在32位模式下编译或运行时才有效。 - Lamar
我刚刚测试了这个连接并且在Windows Server 2008 R2 x64 RC上出现故障,似乎必须安装2007 Office System驱动程序:数据连接组件[microsoft.com/downloads/... - Chris Richner
要非常小心 - 这是一个很难看的丑陋(例如,有时它会猜测一个列类型并丢弃所有不适合的数据)。 - dbkk
如果使用这种方法,应该非常小心。我发现它对于不是完美格式的数据非常不稳定。 - Kenny Mann
作为一个必须在一个大项目中使用OleDb的人,我说要远离它!它有时无法仅因为无法理解格式而检索单元格值。它没有删除操作。即使只有最轻微的提供商改变,它的工作方式也完全不同且不可预测。我想说一个经过验证的商业解决方案。 - Caner Öncü


商业解决方案, SpreadsheetGear for .NET 会做的。

您可以看到实时ASP.NET(C#和VB)示例 这里 并下载评估版 这里

免责声明:我拥有SpreadsheetGear LLC


73



你有一个很棒的产品,但我想很多人都期待免费的解决方案。这可能解释了下来的选票。 - md1337


我用过的几个选项:

如果XLSX是必须的: ExcelPackage 是一个良好的开端,但在开发人员退出工作时就已经死了。 ExML从那里获得并添加了一些功能。 EXML 这不是一个糟糕的选择,我仍然在几个生产网站中使用它。

但是,对于我所有的新项目,我都在使用 NPOI,.NET的端口 Apache POINPOI 2.0(Alpha) 还支持XLSX。


56



如果需要支持XLS,请小心使用ExcelPackage。我很难用它,最终切换到ExcelLibrary。 - Jeremy
绝对真实。如果您需要XLSX支持,ExcelPackage / ExML只是一个不错的选择。 - Nate
请注意,ExcelPackage有一个后继者:EPPlus(epplus.codeplex.com)支持XLSX。与NPOI相比,我唯一担心的是性能,例如什么时候有很多专栏。 - Pragmateek


一个非常轻量级的选项可能是使用HTML表。只需在文件中创建head,body和table标签,并将其另存为扩展名为.xls的文件。您可以使用Microsoft特定属性来设置输出样式,包括公式。

我意识到您可能不会在Web应用程序中对此进行编码,但这是一个  通过HTML表格的Excel文件的组成。如果您正在编写控制台应用程序,桌面应用程序或服务,则可以使用此技术。


54



它是如此临时但它的工作原理(更不用说excel在开启时发出警告)并且非常简单,它应该有一个地方作为解决方案。虽然只是为了表明你可以导出一个excel文件:)) - Luka Ramishvili
这个解决方案对我来说很好,只需注意你不能使用.xlsx扩展名 - Jill
我的组织中的某些人无法在Office 2010及更高版本中以这种方式打开excel文件。不知道问题是什么,但我不得不推出自己的OpenXML实现。 (见Sogger的回答) - Kristen Hammack