在.NET中,线程完成任务后会发生什么?我需要管理吗?

ant*_*ell 8 c# multithreading

在完成Console.WriteLine(暂停它或其他东西)后,我是否需要对此线程执行某些操作?或者垃圾收集是否会启动并删除此线程?

public void testThreading() {

    .. do some stuff

    var t = new Thread(() => { Console.WriteLine("hey!"); })
    t.Start();

}
Run Code Online (Sandbox Code Playgroud)

Ant*_*ell 8

简答:

当一个线程完成它的进程时,如果没有别的东西持有它的引用,垃圾收集器将自动处理它.

答案很长:

垃圾回收器由CLR初始化后,它会分配一段内存来存储和管理对象.此内存称为托管堆,而不是操作系统中的本机堆.每个托管进程都有一个托管堆.

进程中的所有线程都为同一堆上的对象分配内存.为了保留内存,垃圾收集器调用Win32 VirtualAlloc函数,并为托管应用程序一次保留一段内存.垃圾收集器还根据需要保留段,并通过调用Win32 VirtualFree函数将段释放回操作系统(在清除任何对象之后).堆上分配的对象越少,垃圾收集器的工作就越少.分配对象时,请不要使用超出需求的舍入值,例如在只需要15个字节时分配32个字节的数组.当触发垃圾收集时,垃圾收集器回收死对象占用的内存.

回收过程压缩活动对象,使它们一起移动,并移除死区,从而使堆更小.这可确保一起分配的对象在托管堆上保持一致,以保留其位置.垃圾收集的侵入性(频率和持续时间)是分配量和托管堆上的幸存内存量的结果.堆可以被认为是两个堆的堆积:大对象堆和小对象堆.大对象堆包含85,000字节或更大的非常大的对象.大对象堆上的对象通常是数组.实例对象很少是非常大的.

参考

http://msdn.microsoft.com/en-us/library/ee787088.aspx


Rah*_*thi 5

这里:-

托管线程的生命周期独立于创建它的 Thread 对象,这是一件非常好的事情,因为您不希望 GC 仅仅因为丢失了对关联 Thread 对象的所有引用而终止仍在工作的线程。因此 GC 正在收集 Thread 对象,而不是实际的托管线程。 ......................

托管线程不会退出(并且不会释放其线程堆栈的内存),直到其 ThreadProc 返回或被显式终止。因此,如果托管线程未正确终止,分配给其线程堆栈的内存将会泄漏。

  • 我相信关键短语在该段落的末尾:“*托管线程不会退出(并且其线程堆栈的内存不会释放),直到其 ThreadProc 返回或被显式终止。* ***因此,如果托管线程未正确终止,分配给其线程堆栈的内存将泄漏。***”因此,正如您正确指出的那样,当“Thread”对象超出范围时,它*不会*被清理,而是当`ThreadProc` 退出。 (2认同)