杀死Excel的错误

我希望你能帮助我,在过去你们都很棒。 我已经尝试了从vb.net杀死excel的杀死脚本的每个变种,都没有用。

首先,我不能在这里发布明确的代码,因为这是我公司的专有软件,但我可以告诉你一些事情。 还有超过28000行的代码。

  1. 我不使用

    Imports Excel = Microsoft.Office.Interop.Excel 

    由于我们必须适应客户端软件的不同变化。 我正在创造新的excel作为一个对象

     Dim XLObj As Object = CreateObject("Excel.Application") 

    我已经看到这在其他几个网站上使用,但他们正在使用的杀人function是当你保存,然后closures它,我不这样做。

  2. 我得到的错误信息说“已经从它的底层RCW分离的COM对象不能使用”。 我不确定这个COM对象是在哪里,因为我已经发布了工作表,工作簿,然后是应用程序。

  3. 哦,我不想使用excel.kill(),因为如果客户端已经打开了excel,我不想在不保存的情况下杀死它。 我只想杀死新生成的没有与之关联的窗口的excel进程。

我的问题如下

  1. 如果打开失败,我需要能够closuresExcel应用程序。 所以说,我点击一个链接,它打开对话框来select要加载的Excel模板,但是从数据库中的数据已损坏或SQL语句已损坏。 程序抛出错误,然后Excel应该closures在任务pipe理器中。 不幸的是,这并不能解决问题。

  2. 有没有办法只closures新创build的进程ID? 我试图使用这里的方向但它也不工作。 当我这样做,它给了我一个不同的错误“值不能为空参数名称:o”。 抛出错误的行是(从链接)

     Marshal.FinalReleaseComObject(tempVar) 

    我只试过这个,因为我们在XLObj上使用With。 With是参考工作簿本身,所以当我closures工作簿时不应该发布它? 正因为我目前正在故意造成错误,所以无论如何都不应该达到With声明。

  3. 有没有办法告诉哪个com对象不closures?

我已经尝试过的事情:

  1. 这个释放对象,我在互联网上find。 (不要问我在哪里经历了大约75页)

     Private Sub releaseObject(ByRef obj As Object) Try System.Runtime.InteropServices.Marshal.FinalReleaseComObject(obj) If obj Is Nothing Then Else obj = Nothing End If Catch ex As Exception If obj Is Nothing Then Else obj = Nothing End If Finally GC.Collect() GC.WaitForPendingFinalizers() End Try End Sub 

这是与这个function(这是从我一直在许多网站拼凑在一起)

  Public Sub CloseExcel(ByRef WorkBook As Object, ByRef Application As Object) Dim xLSheet As Object = WorkBook.Sheets For Each xLSheet In WorkBook.Sheets If xLSheet IsNot Nothing Then releaseObject(xLSheet) End If If xLSheet IsNot Nothing Then Kill(xLSheet) End If Next If WorkBook IsNot Nothing Then WorkBook.Close(False) End If If WorkBook IsNot Nothing Then Kill(WorkBook) End If releaseObject(WorkBook) If Application IsNot Nothing Then Application.Quit() End If If Application IsNot Nothing Then Kill(Application) End If releaseObject(Application) GC.Collect() GC.WaitForPendingFinalizers() Application.Quit() End Sub 

因为它也被引用了杀戮function

  Public Sub Kill(ByRef obj As Object) Try System.Runtime.InteropServices.Marshal.FinalReleaseComObject(obj) Catch ex As Exception MessageBox.Show("moduleExcel.Kill " & ex.Message) Finally obj = Nothing End Try End Sub 

任何帮助将不胜感激。

好吧,对于那些有这个完全相同的问题。 我有你的解决scheme。 是的,上面的代码确实有效,但只做了一些小的调整。

  1. 您需要取出CloseExcel子版中的所有代码,并将其正确放置在您希望closures的位置。 所以如果你想把它closures,如果程序出错了,放在catch语句之后。 你不能调用一个Sub并传入你的对象,并期望它杀死这个进程。

  2. 您需要在新Excel过程的开头之上几位。 他们如下。

     'declare process for excel Dim XLProc As Process 'loads the financials excel bookmarks 'this will be where you declare your new excel opbject Dim XLObj As Object = CreateObject("Excel.Application") 'get window handle Dim xlHWND As Integer = XLObj.hwnd Dim ProcIDXL As Integer = 0 'get the process ID GetWindowThreadProcessId(xlHWND, ProcIDXL) XLProc = Process.GetProcessById(ProcIDXL) 

当然你需要从原始问题中包含的链接中获取GetWindowThreadProcessId。 我在这里发布,所以你不必去search它。

  <System.Runtime.InteropServices.DllImport("user32.dll", SetLastError:=True)> _ Private Function GetWindowThreadProcessId(ByVal hWnd As IntPtr, ByRef lpdwProcessId As Integer) As Integer End Function 

此代码只会closures您关联的单个进程,不会closures其他打开的Excel文件。 我们的客户有时会打开多个文件,我们不想不告诉他们就closures它们。 这KILLS系统错误时运行时创build的Excel进程。