如何实例化一个名为Excel.Application的对象,以允许在意外之后进行宏后垃圾回收

时间:2012-01-21 01:22:25

标签: excel excel-vba excel-2003 vba

我是一个相对VBA的新手,设计一个相当复杂的宏,可以在10秒到10分钟之间运行任何东西,它的大部分工作都在Dim appDatabaseInstance = New Excel.Application创建的另一个不可见的Excel实例中。在代码执行过程中会使用许多函数和子例程,虽然我已经尽力确保在任何半可预测的错误时调用appDatabaseInstance.Quit,但有一件事我可以' t控制 - 用户。

具体来说,如果用户判定程序已崩溃并保持转义,VBA将中断执行,并且由于中断的发生方式,我的垃圾收集程序(我认为)都没有结束。

因此,如果我能以某种方式命名我以可预测的方式创建的实例,然后在创建新实例之前尝试找到现有实例并适当地处理它,我会更高兴。这样即使一个不幸的应用程序实例保持打开状态,一旦用户尝试涉及该程序的任何其他内容,它将立即关闭(如果它们没有,那么一个实例不太可能在上下文中引起太多麻烦)。

有人有任何建议吗?

2 个答案:

答案 0 :(得分:6)

您可以使用Application对象的EnableCancelKey属性来确定用户中断代码时会发生什么

我建议您在Dick博客上看到this post on EnableCancelKey

总结一下,EnableCancelKey有三种可能的设置:

  • xlDisable - 防止用户中断代码
  • xlInterrupt - 正常运行。显示调试器,代码处于调试模式,无论它在中断时发生的是哪一行。
  • xlErrorHandler - 引发错误编号18并像其他任何错误一样做出反应。如果您设置了错误处理,则会调用它。

答案 1 :(得分:3)

之前我必须在VBA中做类似的事情。 follow方法将关闭除当前正在运行代码的进程之外的所有其他excel进程。 在尝试运行此代码之前,请记得保存您的资料!

Declare Function GetCurrentProcessId Lib "kernel32" () As Long

Sub CloseOtherInstances()

  Dim currentId As Long
  Dim wmiObj As Object
  Dim process As Object
  Dim processes As Object

  currentId = GetCurrentProcessId

  Set wmiObj = GetObject("winmgmts:{impersonationLevel=impersonate}!\\.\root\cimv2")

  Set processes = wmiObj.ExecQuery("select * from win32_process where name ='EXCEL.exe'")

  For Each process In processes
    If process.ProcessId <> currentId Then process.Terminate
  Next process

End Sub