2010-08-31 123 views

回答

54

术语“非托管资源”通常用于描述不直接处于垃圾收集器的控制下的东西。例如,如果打开与数据库服务器的连接,则会使用服务器上的资源(用于维护连接)以及客户端计算机上的其他非.NET资源(如果提供程序未完全用托管代码写入)。

这是为什么,像一个数据库连接,建议你写的正是如此代码:

using (var connection = new SqlConnection("connection_string_here")) 
{ 
    // Code to use connection here 
} 

因为这确保.Dispose()被称为连接对象上,确保任何非托管资源的及时清理。

+8

我会稍微澄清一点:“非托管资源”是垃圾收集器在丢弃之后不知道如何清理的内容。例如,短暂对象从长寿命对象订阅事件,即使两个对象都处于垃圾收集器的控制之下,也是非托管资源,因为GC无法知道订阅如果订阅者被放弃但发行者不在,应该报废。如果在发布者的生命周期中可以创建和放弃无限数量的订阅者,那会导致内存泄漏。 – supercat 2011-08-12 19:47:43

+8

增加一点说明:SqlConnection(或FileStream等)是管理资源,它们在内部使用GC不知道的非托管资源。 – jimvfr 2013-01-17 02:21:23

+1

jimvfr是对的,SqlConnection是一个管理资源的例子。非托管资源的一个例子是,当我们需要使用Marshal.AllocHGlobal()方法从非托管内存分配内存时,在这种情况下,最好的做法是使用析构函数(〜ctor)并调用Marshal.FreeHGlobal()释放这个内存。 – 2014-07-30 17:13:31

23

管理资源是那些纯粹的.NET代码,由运行时管理并受其直接控制。

非托管资源是那些不是。文件句柄,固定内存,COM对象,数据库连接等。

6

之间的基本差异托管和非托管资源就是 垃圾收集知道的所有管理资源,在某个时间点 的GC会来清理所有的内存和相关 与被管理对象资源。 GC不知道非托管资源,例如 作为文件,流和句柄,所以如果您没有明确地清除它们在 您的代码,那么您将最终与内存泄漏和锁定的资源。

详情 - http://bytes.com/topic/c-sharp/answers/276059-what-unmanaged-resources

+1

“IDisposable接口背后的想法是让您以确定性的方式清理资源并清理非托管资源。”真棒! – zionpi 2013-11-14 06:53:02

0

管理的资源是可以被垃圾收集器被释放和非托管资源能为需要为此析构函数不会被垃圾收集器释放的资源。

4

在问答&一个What are unmanaged resources?布鲁斯·伍德贴内容:

我认为术语 “管理” 和 “非托管” 这种方式:

“管理“引用.NET沙箱中的任何内容。这包括所有.NET Framework类的 。

“非托管”指的是.NET沙箱之外的荒野。此 包括通过调用Win32 API 函数返回给您的任何内容。

如果从未调用Win32 API函数和从未取回任何的Win32 “处理”的对象,那么你就不会持有任何非托管资源。 通过.NET Framework类方法打开的文件和流为 所有托管包装。

评论:您可能没有持有非托管资源直接。但是,您可能会通过托管的“包装类”(例如System.IO.FileStream)间接持有非托管资源。这样的包装类通常实现IDisposable(直接或通过继承)。

...许多管理(.NET Framework)的对象 持有非托管资源在他们里面,你可能马上要他们的 Dispose()方法就可以了,或者至少提供来电者 的有机会这样做。这就是写自己的Dispose() 方法来在本质上,实施了IDisposable()做了两米 你的东西:

  1. 让您摆脱任何资源可以直接从 操作系统后面抓住.NET的背后(非托管资源)。

  2. 让您和您调用者释放沉重的.NET对象/ .NET 对象在他们的肮脏的小 手中拿着宝贵的资源,你/你的来电者想要发布现在

评论:通过实施IDisposable从而提供一个Dispose()方法,你让你的类在确定性时尚释放被持有的非托管资源的用户通过一个实例类。


链路最初在Sachin Shanbhag's answer共享。引用日期为2005-11-17的材料。请注意,我轻轻地复制了所引用的内容。