C# VSTO中的WPF应用程序未被垃圾收集
因此,我正在使用C#和WPF为Office构建应用程序(通过VSTO)。我发现WPF应用程序(通过内存分析器)在启动后从未被收集 我将为WPF应用程序创建一个新的AppDomain,在该AppDomain中启动它,并在使用之后卸载AppDomain,但我仍然有对象在周围--我的句柄仍然在增大 有人知道VSTO和WPF应用程序有什么奇怪的行为吗?我唯一的猜测是,出于某种原因,WPF应用程序被加载到Office共享的UI线程上,因此它永远不会被清理 关于增加手柄有什么想法吗?我的客户的部署团队强烈反对“增加手柄是不可接受的” 编辑:C# VSTO中的WPF应用程序未被垃圾收集,c#,wpf,vsto,C#,Wpf,Vsto,因此,我正在使用C#和WPF为Office构建应用程序(通过VSTO)。我发现WPF应用程序(通过内存分析器)在启动后从未被收集 我将为WPF应用程序创建一个新的AppDomain,在该AppDomain中启动它,并在使用之后卸载AppDomain,但我仍然有对象在周围--我的句柄仍然在增大 有人知道VSTO和WPF应用程序有什么奇怪的行为吗?我唯一的猜测是,出于某种原因,WPF应用程序被加载到Office共享的UI线程上,因此它永远不会被清理 关于增加手柄有什么想法吗?我的客户的部署团队强烈反
让我澄清一下——WPF应用程序是从功能区启动的,然后它们在各自的应用程序中生成输出,即,如果在Excel中,您将输入信息,然后它将根据提供的信息为您构建电子表格;如果在PowerPoint中,您将输入信息(在从功能区启动的WPF应用程序中),它将根据您提供的信息生成幻灯片。我的理解是,VSTO解决方案(至少在Visual Studio 2010中)始终使用将VSTO外接程序加载到单独的AppDomain中。这种隔离保护您的外接程序不受其他外接程序的任何不稳定影响 可能是由于与VSTO主机应用程序(例如Excel)交互时创建了隐藏的运行时可调用包装器(RCW),应用程序的内存使用量在不断增加 我的第一个VSTO应用程序最初依赖于
Marshal.ReleaseComObject()
来释放RCW,但是,基于这些博客文章,我将我的方法改为使用以下方法:
公共静态类OfficeHelper
{
///
///强制GC释放COM对象周围未使用的运行时可调用包装器
///
///
///动态rcw;
///试一试
/// {
///rcw=Globals.ThisWorkbook.ActiveSheet;
/////做点什么
/// // ...
/// }
///最后
/// {
///rcw=null;
///OfficeHelper.Cleanup();
/// }
///
公共静态无效清除()
{
System.Diagnostics.Debug.Print(“OfficeHelper::Cleanup-gcforced”);
GC.Collect();
GC.WaitForPendingFinalizers();
System.Diagnostics.Debug.Print(“OfficeHelper::Cleanup-GC finished”);
}
}
到目前为止,这种方法在我的应用程序中运行良好,GC时间比我预期的要快。实际上,在每个应用程序“结束”后,我都有这两行代码。。。但是我仍然看到句柄/内存/等的增加。内存不是一个大问题,但句柄似乎是。From:>Visual Studio Tools for Office创建一个新的AppDomain以加载每个VSTO加载项。因此,它不会相互影响。程序员不需要担心“Outlook不会关闭”的问题。当VSTO加载项关闭时,AppDomain将被卸载,它将回收程序员在应用程序中分配的资源。如果我们从VSTO功能区启动应用程序,从而创建幻灯片/输出,会怎么样?i、 e.单击VSTO功能区上的按钮,然后它会启动一个应用程序,该应用程序会获取一些信息并自动生成具有互操作类型的幻灯片?