将 office 应用程序不会不会退出后从 Visual Studio.net 客户端的自动化

注意:这篇文章是由无人工介入的微软自动的机器翻译软件翻译完成。微软很高兴能同时提供给您由人工翻译的和由机器翻译的文章, 以使您能使用您的语言访问所有的知识库文章。然而由机器翻译的文章并不总是完美的。它可能存在词汇,语法或文法的问题,就像是一个外国人在说中文时总是可能犯这样的错误。虽然我们经常升级机器翻译软件以提高翻译质量,但是我们不保证机器翻译的正确度,也不对由于内容的误译或者客户对它的错误使用所引起的任何直接的, 或间接的可能的问题负责。

点击这里察看该文章的英文版: 317109
本文已归档。它按“原样”提供,并且不再更新。
症状
自动执行从一个 Microsoft Office 应用程序时Microsoft Visual Basic.net Microsoft Visual C#,Office 应用程序不会不会退出时调用Quit方法。
原因
当 Visual Studio.net 调用 COM 对象从托管代码,它会自动创建运行时可调用包装 (RCW)。RCW封送.net 应用程序和 COM 对象之间的调用。RCW 保留对 COM 对象的引用计数。因此,如果未进行的所有引用释放对 RCW,COM 对象不会不会退出。
解决方案
若要确保 Office 应用程序退出,请确保验证您自动化代码是否符合以下条件:
  • 为新变量声明的每个对象。例如,更改下面的代码行
    oBook = oExcel.Workbooks.Add()					
    为以下值:
    dim oBooks as Excel.WorkbooksoBooks = oExcel.WorkbooksoBook = oBooks.Add()					
  • 使用 System.Runtime.InteropServices.Marshal.ReleaseComObject 在循环中直到完成后使用一个对象,则返回 0。" System.Runtime.InteropServices.Marshal.ReleaseComObject 递减 RCW,而该环路的引用计数将确保基础 COM 组件被释放而不考虑如何重新很多时候它已输入 CLR。
  • 若要解除对变量的引用,设置变量等于 执行任何操作空值.
  • 使用 退出 告诉服务器到 Office 应用程序对象的方法关闭。
状态
这行为是设计使然。
更多信息

要重现此问题的步骤

  1. Visual Studio.net 的开始。
  2. 文件菜单上单击新建,然后单击项目。在Visual Basic 项目,下面,选择Windows 应用程序并单击确定。默认情况下,将创建 Form1。
  3. 添加到Microsoft Excel 对象库的引用。请执行以下步骤:
    1. 项目菜单中,单击添加引用
    2. COM选项卡上的 Excel 中,定位对象库,然后单击选择

      Microsoft Excel 2002: Microsoft Excel 10.0 对象库

      注意如果您还没有这样做,则建议您下载并安装 Microsoft Office XP 主 Interop 程序集 (Pia)。 有关 Office XP Pia 的其他信息,请单击下面的文章编号,以查看 Microsoft 知识库中相应的文章:
      328912Microsoft Office XP 主 interop 程序集 (Pia) 将可供下载
      对于 Microsoft Office,Excel 2003: Microsoft Excel 11.0 对象库
    3. 单击确定添加引用对话框中接受您的选择。
  4. 视图菜单中,单击工具箱,然后拖到 Form1 上拖动一个按钮控件。
  5. 双击Button1。此时将显示窗体的代码窗口。
  6. 到 Form1.vb 的顶部添加以下代码:
    Imports Microsoft.Office.Interop					
  7. 在代码窗口中将以下代码
        Private Sub Button1_Click(ByVal sender As System.Object, _       ByVal e As System.EventArgs) Handles Button1.Click    End Sub					
    与以下内容:
    Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click    Dim oApp As New Excel.Application()    Dim oBook As Excel.Workbook = oApp.Workbooks.Add    Dim oSheet As Excel.Worksheet = oApp.ActiveSheet    oSheet = Nothing    oBook.Close(False)    oBook = Nothing    oApp.Quit()    oApp = Nothing    Debug.WriteLine("Sleeping...")    System.Threading.Thread.Sleep(5000)    Debug.WriteLine("End Excel")End Sub					
  8. 按 F5 键运行该应用程序。
  9. 打开 Windows 任务管理器。在 Visual Studio,显示输出窗口以查看调试消息。单击命令按钮,请注意,在进程列表中显示 Excel.exe 实例。
  10. Excel 的实例仍运行在任务列表中甚至之后在应用程序完成休眠。关闭对话框,请注意,Excel 不会再出现在进程列表中。
  11. 当在"解决办法"部分中,实现相应的步骤Office 应用程序退出后释放最后一个变量。替换函数在步骤 5 中,用下面的代码:
      Private Sub NAR(ByVal o As Object)    Try      While (System.Runtime.InteropServices.Marshal.ReleaseComObject(o) > 0)      End While    Catch    Finally      o = Nothing    End Try  End SubPrivate Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click    Dim oApp As New Excel.Application()    Dim oBooks As Excel.Workbooks = oApp.Workbooks    Dim oBook As Excel.Workbook = oBooks.Add    Dim oSheet As Excel.Worksheet = oApp.ActiveSheet    NAR(oSheet)    oBook.Close(False)    NAR(oBook)    NAR(oBooks)    oApp.Quit()    NAR(oApp)    Debug.WriteLine("Sleeping...")    System.Threading.Thread.Sleep(5000)    Debug.WriteLine("End Excel")End Sub					
如果您使用的 Visual C#.net,引用NAR()函数的代码:
private void NAR(object o){    try     {        while (System.Runtime.InteropServices.Marshal.ReleaseComObject(o) > 0) ;    }    catch {}    finally     {        o = null;    }}
注:从开始.NET Framework 2.0,您可以使用System.Runtime.InteropServices.Marshal.FinalReleaseComObject来代替 while 循环调用System.Runtime.InteropServices.Marshal.ReleaseComObject来实现相同的结果。

故障排除

请注意,如果您按照中所述的步骤"步骤重现行为"一节,并在服务器仍然没有关闭向下,您可以使用GC。Collect()方法和GC。WaitForPendingFinalizers()后释放的最后一个对象的方法。因为运行库对GC,RCW 执行垃圾回收。Collect()方法强制垃圾回收器在运行,并可能释放任何仍有 RCW 的引用。GC。Collect()方法尝试回收可用的最大内存。请注意,这不能保证所有内存都被都回收。
gc.collect ReleaseComObject ;FinalReleaseComObject

警告:本文已自动翻译

属性

文章 ID:317109 - 上次审阅时间:12/07/2015 08:49:07 - 修订版本: 1.0

Microsoft Visual Basic .NET 2003 标准版, Microsoft Visual C# .NET 2003 标准版, Microsoft Visual .NET 2002 标准版, Microsoft Visual C# .NET 2002 标准版

  • kbnosurvey kbarchive kbautomation kbprb kbmt KB317109 KbMtzh
反馈