首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >从新线程中处理ExcelDnaUtil.Application

从新线程中处理ExcelDnaUtil.Application
EN

Stack Overflow用户
提问于 2014-08-21 19:55:35
回答 1查看 846关注 0票数 2

我正在使用ExcelDNA开发一个XLL。

在它中,我有一个存在于DLL中的表单,我将"ExcelDnaUtil.Application“作为成员传递给它,以方便运行XLL的表单和实例之间的交互。

如果我使用以下方法在主线程中启动表单:

代码语言:javascript
运行
复制
form1.show()

当我关闭窗体然后关闭Excel时,显示Excel进程已被正确处理。

如果我使用一个新线程启动表单:

代码语言:javascript
运行
复制
Dim workerThread As Thread
workerThread = New Thread(Sub() form1.showdialog())
workerThread.Start()

当我关闭窗体然后关闭Excel时,进程将保留在中。我非常小心,不要在任何代码行中使用两个小数点,并在关闭表单时将接口成员设置为"nothing“。我没有像其他文章指出的那样使用"ReleaseCOMObject“--实践是错误的。

问:我如何正确地从一个单独的线程处理Excel进程?

EN

Stack Overflow用户

回答已采纳

发布于 2014-08-21 21:16:28

这是不可能得到正确的COM的东西横线。

您不应该从另一个线程与Excel对象模型对话。如果您遵循这条简单的规则,您就不必担心两个点,也不必将任何东西设置为零,也不必调用任何ReleaseComObject黑客。Excel会很好地关闭。

由于Excel是单线程的(实际上是因为Excel对象模型驻留在一个单线程的单元中),与另一个线程对话对性能没有好处--在内部,所有这些都被编组到主线程。

如果您敢从另一个线程与Excel对话,那么任何COM调用都可能在任何时候失败。这是因为Excel仍然处于“活动状态”,可以进入“对象模型挂起”的状态,从而导致所有COM调用失败(即使是COM消息筛选器也无法捕获错误)。Excel何时会进入如此顽固的模式?例如,当用户做一些疯狂的事情,比如点击他们的鼠标按钮。

那么,在您对另一个线程做了一些工作之后,如何调用Excel呢?Excel-DNA有一个助手,当Excel处于COM调用是安全的模式时,它将安排在主线程上完成的工作。您只需使用包含要完成的工作的委托调用ExcelAsyncUtil.QueueAsMacro(...)。这个调用可以在任何时候从任何线程进行,但是代码只有在准备就绪时才会运行。

一个有点笨拙的例子是:

代码语言:javascript
运行
复制
Public Module MyFunctions

    Dim workerThread As Thread

    Public Function OverwriteMe() As Object
        Dim caller = ExcelDnaUtil.Application.Caller
        workerThread = New Thread( _
            Sub()
                Thread.Sleep(5000)
                ExcelAsyncUtil.QueueAsMacro( _
                    Sub()
                        caller.Value = "Done!!!"
                    End Sub)
            End Sub)
        workerThread.Start()
        Return "Doing it..."
    End Function
End Module
票数 2
EN
查看全部 1 条回答
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/25434845

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档