Tag: garbage collection

C#:在什么情况下你应该删除引用?

CLR Profiler还可以显示哪些方法分配的存储空间超出了您的预期,并且可以发现无意中保留对无用的对象图的引用的情况,否则这些对象图可能被GC回收。 (一个常见的问题设计模式是一个软件缓存或项目的查找表,这些项目不再需要或以后可以安全重建。当缓存使对象图表保持活动超过其使用寿命时,这是悲剧性的。相反,请确保将参考文献归零到你不再需要的对象 。) – 编写更快的托管代码 我认为我之前没有真正搞过一个参考。 我假设你并不总是需要这样做,但我想也有时候记得这么做很重要。 但是,那是什么情况呢? 什么时候应该删除引用?

追踪内存泄漏(C#)的最佳方法仅在一个客户的盒子上可见

追踪只能在一个客户的测试/发布盒中找到的内存泄漏的最佳方法是什么,而在其他地方没有?

GC行为和CLR线程劫持

我正在CLR via C#阅读CLR via C#一书中关于GC的内容,特别是关于CLR何时想要开始收集的内容。 我知道它必须在收集发生之前挂起线程,但它提到它必须在线程指令指针到达安全点时执行此操作。 在它不在安全点的情况下,它会尝试快速找到一个,并通过hijacking线程(在线程堆栈中插入一个特殊的函数指针)来实现。 这一切都很好,花花公子,但我认为托管线程默认是安全的? 我最初认为它可能是指非托管线程,但CLR允许非托管线程继续执行,因为任何使用的对象都应该被固定。 那么,托管线程中的safe point是什么,GC如何确定它是什么? 编辑: 我认为我不够具体。 根据这篇MSDN文章 ,即使调用Thread.Suspend ,在达到safe point之前,线程实际上不会被挂起。 它继续进一步说明safe point是线程执行中可以执行垃圾收集的点。 我想我的问题不清楚。 我意识到一个线程只能在安全点暂停,并且它们必须暂停用于GC,但我似乎无法找到一个明确的答案,关于什么是安全点。 是什么决定了代码中的安全点?

有人可以解释垃圾收集器的行为吗?

我正在玩C#中的垃圾收集器(或者更确切地说是CLR?)试图更好地理解C#中的内存管理。 我做了一个小样本程序,它将三个较大的文件读入byte[]缓冲区。 我想看看,如果 我实际上需要做任何事情来处理内存效率 在当前迭代结束后将byte[]设置为null时会产生任何影响 最后,如果它有助于通过GC.Collect()强制垃圾收集 免责声明:我使用Windows任务管理器测量内存消耗并将其四舍五入。 我尝试了好几次,但总的来说还是差不多。 这是我的简单示例程序: static void Main(string[] args) { Loop(); } private static void Loop() { var list = new List { @”C:\Users\Public\Music\Sample Music\Amanda.wma”, // Size: 4.75 MB @”C:\Users\Public\Music\Sample Music\Despertar.wma”, // Size: 5.92 MB @”C:\Users\Public\Music\Sample Music\Distance.wma”, // Size: 6.31 MB }; Console.WriteLine(“before loop”); Console.ReadLine(); foreach (string pathname in list) { […]

C#和.Net垃圾收集器性能

我正在尝试用C#和.NET制作游戏,并且我计划实现更新游戏世界中游戏对象的消息。 这些消息将是C#引用对象。 我想要这种方法,因为如果我想让游戏成为多人游戏,那么这样做会更容易通过网络发送它们。 但是,如果我有很多消息,对垃圾收集器来说难道不会很紧张吗? 这不会影响游戏玩法吗? 消息类本身很小,最多只有4或5个成员。 对于游戏世界中的每个对象,这些消息将每秒生成几次。

什么是GC孔?

我用C#写了一个很长的TCP连接套接字服务器。 我的服务器内存中出现峰值。 我使用dotNet Memory Profiler(一种工具)来检测内存泄漏的位置。 内存分析器指示私有堆很大,内存类似于下面(数字不是真实的,我要显示的是GC0和GC2的孔非常大,数据大小正常): Managed heaps – 1,500,000KB Normal heap – 1400,000KB Generation #0 – 600,000KB Data – 100,000KB “Holes” – 500,000KB Generation #1 – xxKB Data – 0KB “Holes” – xKB Generation #2 – xxxxxxxxxxxxxKB Data – 100,000KB “Holes” – 700,000KB Large heap – 131072KB Large heap – 83KB Overhead/unused – 130989KB […]

C#Action,Closure和Garbage Collection

我是否需要将MyAction设置为null,以便垃圾收集能够继续使用这些类中的任何一个? 当两个class级的生命周期几乎相同时,我不太关心。 当Class1的寿命比Class2长得多或者Class2的寿命比Class1长得多时,我的问题更合适。 这里的代码被删除了。 假设Class1和Class2都包含可能影响其生命周期的其他成员和方法。 public class Class1 : IDisposable { public Action MyAction { get; set; } // Is this necessary? public void Dispose() { MyAction = null; } } public class Class2 { string _result = string.Empty; public void DoSomething() { Class1 myClass1 = new Class1(); myClass1.MyAction = s => _result = s; […]

.NET 4垃圾收集器的可伸缩性

我最近对.NET 4垃圾收集器进行了基准测试,从多个线程中集中分配。 当分配的值记录在一个数组中时,我没有像我预期的那样观察到没有可伸缩性(因为系统争用对共享旧代的同步访问)。 但是,当分配的值立即被丢弃时,我惊恐地发现没有可扩展性! 我曾预计临时案例几乎是线性扩展的,因为每个线程应该简单地擦除托儿所gen0干净并重新开始而不争用任何共享资源(没有任何东西幸存到老一代并且没有L2缓存未命中因为gen0很容易适合L1缓存)。 例如, 这篇MSDN文章说 : 无同步分配在多处理器系统上,托管堆的第0代将被分成多个内存竞技场,每个线程使用一个竞技场。 这允许多个线程同时进行分配,因此不需要对堆进行独占访问。 任何人都可以validation我的发现和/或解释我的预测和观察之间的这种差异吗?

为什么Roslyn中有如此多的对象池实现?

ObjectPool是Roslyn C#编译器中使用的一种类型,用于重用经常使用的对象,这些对象通常会被新用起来并经常收集垃圾。 这减少了必须发生的垃圾收集操作的数量和大小。 Roslyn编译器似乎有几个单独的对象池,每个池有不同的大小。 我想知道为什么有这么多的实现,首选的实现是什么,以及为什么他们选择了20,100或128的池大小。 1 – SharedPools – 如果使用BigDefault,则存储20个对象的池或100个。 这个也很奇怪,因为它创建了一个新的PooledObject实例,当我们试图聚集对象而不是创建和销毁新对象时这没有任何意义。 // Example 1 – In a using statement, so the object gets freed at the end. using (PooledObject pooledObject = SharedPools.Default<List>().GetPooledObject()) { // Do something with pooledObject.Object } // Example 2 – No using statement so you need to be sure no exceptions are […]

创建对IObservable的弱订阅

我想要做的是确保如果对我的观察者的唯一引用是可观察的,它会被垃圾收集并停止接收消息。 假设我有一个带有列表框的控件,名为Messages,后面是这个代码: //Short lived display of messages (only while the user’s viewing incoming messages) public partial class MessageDisplay : UserControl { public MessageDisplay() { InitializeComponent(); MySource.IncomingMessages.Subscribe(m => Messages.Items.Add(m)); } } 哪个连接到此来源: //Long lived location for message store static class MySource { public readonly static IObservable IncomingMessages = new ReplaySubject; } 我不想要的是让消息显示器在不再可见后很长时间内保存在内存中。 理想情况下,我想要一点延伸,所以我可以写: MySource.IncomingMessages.ToWeakObservable().Subscribe(m => Messages.Items.Add(m)); […]