为什么将我的WPF Treeview绑定到LinqToSql类是一个内存猪? [英] Why is my WPF Treeview bound to LinqToSql classes being a memory hog?

查看:75
本文介绍了为什么将我的WPF Treeview绑定到LinqToSql类是一个内存猪?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个WPF应用程序,它在内存用完后会停止运行...
它基本上是一个显示节点的TreeView,它们是Linq To Sql或生成的类ICTemplates.Segment的实例.在OR设计器中,大约有20个表通过关联间接链接到该类.

I have a WPF App which is grinding to a halt after running out of memory...
It is basically a TreeView displaying nodes, which are instances of Linq To Sql OR Generated class ICTemplates.Segment. There around 20 tables indirectly linked via associations to this class in the OR designer.

<TreeView Grid.Column="0" x:Name="tvwSegments" 
                      ItemsSource="{Binding}" 
                      SelectedItemChanged="OnNewSegmentSelected"/>
<HierarchicalDataTemplate DataType="{x:Type local:Segment}" ItemsSource="{Binding Path=Children}"> 
...

// code behind, set the data context based on user-input (Site, Id)
KeeperOfControls.DataContext = from segment in tblSegments
   where segment.site == iTemplateSite && segment.id == iTemplateSid
   select segment;

我在细分类中添加了一个名为Children的显式属性,该属性可查找具有父子记录的另一个表.

I've added an explicit property called Children to the segment class which looks up another table with parent-child records.

public IEnumerable<Segment> Children
{
  get
  {
    System1ConfigDataContext dc = new System1ConfigDataContext();
    return from link in this.ChildLinks
      join segment in dc.Segments on new { Site = link.ChildSite, ID = link.ChildSID } equals new { Site = segment.site, ID = segment.id }
      select segment;
  }
}

其余部分是数据绑定和数据模板,以将每个细分显示为一组UI控件.

The rest of it is data binding coupled with data templates to display each Segment as a set of UI Controls.

我可以肯定的是,在响应时间之前,将按需加载孩子(当我扩展父对象时).当我展开大约有 70 个子节点的节点时,加载子节点需要一段时间(任务管理器显示内存使用情况"为1000000K!).如果我将下一个节点扩展为带有大约50个孩子,那么BOOM! OutOfMemoryException

I'm pretty certain that the children are being loaded on-demand (when I expand the parent) going by the response time. When I expand a node with around 70 children, it takes a while before the children are loaded (Task manager shows Mem Usage as 1000000K!). If I expand the next node with around 50 children, BOOM! OutOfMemoryException

我运行VS Profiler进行了更深入的研究,这是结果

I ran the VS Profiler to dig deeper and here are the results

摘要页面 对象生存期 分配

前3个是Action,DeferredSourceFactory.DeferredSource和EntitySet(所有.Net/LINQ类).唯一的用户类是Segment [],Segment排在#9和#10之间.

The top 3 are Action, DeferredSourceFactory.DeferredSource and EntitySet (all .Net/LINQ classes). The only user-classes are Segment[] and Segment come in at #9 an #10.

我想不出一个追求的线索.可能是什么原因?

I can't think of a lead to pursue.. What could be the reason ?

推荐答案

问题似乎是 Sirocco 所指的多个S1DataContext对象的创建. 我尝试了using语句来强制执行Dispose并使其有资格进行收集.但是,这导致了我无法理解的ObjectDisposedException.

The issue seems to be the creation of multiple S1DataContext objects as Sirocco referred to. I tried the using statement to force a Dispose and make it eligible for collection. However it resulted in an ObjectDisposedException that I can't make sense of.

  1. 控件从设置DockPanel KeeperOfAllControls的数据上下文的行开始.
  2. [外部代码](显示在调用堆栈中)
  3. Segment.Children.get(带有dc的using块)
  4. 返回步骤1中的代码... Linq查询使用tblSegments,它是从S1DataContext的本地实例中检索的.

无论如何,所以我认为有些东西会阻止创建和处置多个DataContext.所以我尝试了Singleton DataContext .
而且有效!

Anyways so i assume that there is something that prevents multiple DataContexts from being created and disposed. So I tried a Singleton DataContext.
And it works!

  • TreeView控件的响应速度明显提高,我尝试的每个节点最多加载3-4秒.
  • 我在每次获取/搜索之前都放入了一个GC.Collect(用于验证),现在内存使用量保持在200,000-300,000K之间.

OR生成的System.Data.Linq.DataContext似乎不会消失,除非将其显式处理(吃掉内存).在我的情况下,尝试将其处置并没有成功..即使两个函数都有自己的using块(没有DataContext的共享实例).尽管我不喜欢Singletons,但我正在为开发人员制作一个小型的内部工具,因此现在不介意..我在网上看到的LinqToSql示例都没有..没有强制执行Dispose调用.

The OR generated System.Data.Linq.DataContext doesn't seem to go away unless it is disposed explicitly (eating memory). Trying to Dispose it in my case, didn't pan out.. even though both functions had their own using blocks (no shared instance of DataContext). Though I dislike Singletons, I'm making a small internal tool for devs and hence don't mind it as of now.. None of the LinqToSql samples I saw online.. had Dispose calls mandated.

所以我想这个问题已经解决.感谢所有为使此错误变得更浅而起更多作用的人们.

So I guess the problem has been fixed. Thanks to all the people that acted as more eyeballs to make this bug shallow.

这篇关于为什么将我的WPF Treeview绑定到LinqToSql类是一个内存猪?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆