【问题标题】:Using Excel as template for .NET code使用 Excel 作为 .NET 代码的模板
【发布时间】:2013-10-25 07:23:50
【问题描述】:

我目前正处于一个应用程序的设计阶段,该应用程序目前在 Excel 中运行。它是一个包含复杂数学(三角、代数等)公式的科学应用程序。最初我尝试在代码中做所有事情,但很快发现将这些科学公式转换为 .NET 会非常繁琐(很有可能出现错误)。

另一种选择是使用 Excel 电子表格及其单元格公式的“模板”,其中 .NET 中的用户界面允许用户输入数据,.NET(网络应用程序)将此输入数据传递给 Excel 电子表格, excel 电子表格完成工作并给出结果,.NET 应用程序读取并显示给用户。 (这是对拟议设计的简化解释)。

它将是 Web 应用程序(不是面向公众的站点)。

其中一个问题(我认为)是当多个用户使用该应用程序时,excel 文件将出现多线程读/写问题。 为了克服这个问题,我想将文件的副本存储在 SQL 数据库中,将其复制到每个会话中使用 Guid 名称(使其唯一)的临时文件夹,并在完成后删除文件等。

我的问题是,有没有人看到这个计划中的任何缺陷或缺点,例如性能、读/写 excel 等或我需要考虑的其他任何事情? 我打算使用 OpenXML 和 ClosedXML 库。我是否需要在部署服务器上安装 Office 才能正常工作? (我本以为不会)。

谢谢,

【问题讨论】:

  • 不要在web环境中使用excel,出现bug的概率是110%...
  • 使用 OpenXML 将避免在服务器上安装 Excel。但是,OpenXML 只允许您修改 Excel 文件。要执行计算,您必须在 Excel 中打开文件,而在 Web 应用程序中执行此操作可能会涉及黑客攻击和挫败感。
  • @MartinLiversage 我认为对于计算部分我可以做这样的事情......stackoverflow.com/questions/2668643/…

标签: asp.net .net multithreading excel openxml


【解决方案1】:

我个人并不认为这是一个坏主意 - 我做了一个应用程序,它生成了数百个电子表格(基于不同用户的一些模板),我使用 ActiveMQ 和 Spring.Net 服务总线使其更快足够 - 通常 3 分钟即可生成 200 多个电子表格:

我有大约 5 台专用服务器将 excel 作为服务运行,前端应用程序只发送请求,不执行电子表格的创建/写入/读取过程。

我遇到的唯一问题是一个 excel 服务一次不能处理超过 10 张纸,否则它会以某种方式崩溃(即使现在也无法弄清楚为什么......)。

谈到安全性和审计,将请求(在您的情况下可能是客户端输入/电子表格实例)存储到数据库中也是一个好主意。

这只是我的经验。忘了说,我用的是 Office Interop 而不是 OpenXML,现在我正在考虑改用 OpenXML。

---- 编辑 ------------- 避免使用多个实例的另一个选择是使用单线程单实例,一个简单的示例(在 vb.Net 中):

Public Class MyCalculator

    Public Class ParamSet
        Property Param1 As Double
        Property Param2 As Long
        ' etc. & etc.
    End Class

    Public Class ResultSet
        Property Output1 As Double
        Property Output2 As Long
        ' etc. & etc.
    End Class

    Private Shared _instance As MyCalculator

    Public Shared Function Calculate(params As ParamSet) As ResultSet
        SyncLock _instance
            Return _instance.DoWork(params)
        End SyncLock
    End Function

    Shared Sub New()
        _instance = New MyCalculator()
    End Sub

    Private Sub New()
        ' Start up excel instance
        ' Set UserControl = true - to make sure it won't be killed by the system automatically
        ' Hold the excel instance in a local variable
    End Sub

    Private Function DoWork(params As ParamSet) As ResultSet
        ' write the params to the excel sheet
        ' then read output you need from corresponding cell
        ' return it out as a result set
    End Function

End Class

单例加上 SyncLock 将确保您拥有一个 excel 实例,并相信它对您的情况来说足够快 - 它只能从 excel 工作表读取/写入,并且 excel 实例将保持在服务器上。

它的好处是您可以轻松地用任何其他方式替换 excel 计算,例如,您自己的实现。

当然,缺点是显而易见的:所有请求都将被一一处理,因为它是单线程的。但我相信它会足够快 - 慢速部分(excel启动)已被取出,现在只能从工作表中读写。关于excel的快速读写,网上有很多资源

【讨论】:

  • 谢谢@Rex,你是说不能在单个网络服务器上处理超过 5 个 excel 副本吗?
  • 我遇到了我的服务服务器 - winXP pro。但我认为您不需要那么多实例,是吗?
  • 另一种选择是使用单例和单线程,并在您的服务器上永久保存一个 excel 实例。我在 vb.net 中做了一个简单的示例,请参阅我帖子的已编辑部分。如果您需要,我可以用 C# 版本制作,只需给我您的电子邮件地址。
  • 我当时的想法是……为每个网络会话打开一个 excel 实例(副本),完成工作,关闭并删除 excel 文件。
  • 我猜你会遇到很多挫折......你无法控制有多少并发会话,尽管它可能适用于你的 DEV 环境,因为你可能一次有一个或两个会话
【解决方案2】:

虽然坚持原来的计划可能很乏味,但它仍然是比读取/写入 Excel 电子表格更好的解决方案。

我相信,如果您足够努力,您会找到将 Excel 电子表格中的公式复制到 .Net 应用程序中的解决方案,此外您还可以将其视为学习曲线。

你有没有遇到过http://linqtocsv.codeplex.com/

如果您打算坚持使用电子表格,这可能对您有所帮助,但是使用带有 .Net 应用程序的 SQL 数据库是一个更强大的系统,并且可以解决多个用户尝试访问您的数据的任何问题。您也可以使用 Entity Framework 或 NHibernate。

Excel 不是为多个用户同时访问而设计的,我认为您最终会遇到很多问题。

【讨论】:

  • 谢谢@Derek,有谁知道任何可以将数学公式(例如从单词)或 Excel 公式转换为 .NET/XML 的库?
【解决方案3】:

如果您在服务器上自动化 Excel,这可能会出现很多问题,那么您可以在每次网页发送请求时启动应用程序的新实例并在该应用程序实例中打开工作簿的副本。对于相当数量的用户来说应该没问题 - 取决于硬件和工作表的大小。

罗斯

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2015-06-26
    • 1970-01-01
    • 2011-06-23
    • 2021-08-23
    • 1970-01-01
    • 1970-01-01
    • 2013-01-14
    相关资源
    最近更新 更多