我的 iDisposable class 中的一次性对象是否保证从内存中释放?
Is a disposable object in my iDisposable class guaranteed to be released from memory?
给出以下 class:
public sealed class DistributedLock : IDisposable
{
private IRedLock Lock { get; }
private bool _disposed;
public DistributedLock(string lockKey, TimeSpan expiry)
{
Lock = RedLockController.GetConnection().CreateLock(lockKey, expiry);
}
private void Dispose(bool disposing)
{
if (_disposed)
return;
if (disposing)
{
if (Lock != null)
{
Lock.Dispose();
}
}
_disposed = true;
}
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
~DistributedLock()
{
Dispose(false);
}
}
其中IRedLock
实现了iDisposable
,而我上面的class的使用方式如下:
using(new DistributedLock("SomeKey"))
{
... do something
}
DistributedLock
和包含的 IRedLock
class 在任何情况下都会从内存中释放吗?
IDisposable
是关于管理除内存以外的资源:比如 GDI 句柄、套接字、文件句柄等。它不会抢占垃圾收集器。所以,IDisposable
只会在两种情况下帮你释放内存:
- 如果您的
IRedLock
类型需要 unmanaged 内存,例如通过第三方库或 unsafe
代码。
- 如果您的
Dispose()
方法从其他对象中清除对该对象的引用,以确保该对象有资格进行垃圾回收,否则可能不会(例如,事件处理程序)。
如果这两者都不适用(并且上面的代码中没有任何内容表明它们适用),那么就内存管理而言,您不会从 IDisposable
中获得任何好处。
您可能会从这段代码中的 IDisposable
中获得一种更好的机制来释放此行中提示的连接:
Lock = RedLockController.GetConnection().CreateLock(lockKey, expiry);
但是,您可能不需要关联的终结器。您只是包装了已经具有终结器的其他东西,因此您可以使用更简单的 IDisposable 模式而不会增加额外的复杂性:
public sealed class DistributedLock : IDisposable
{
private IRedLock Lock { get; }
public DistributedLock(string lockKey, TimeSpan expiry)
{
Lock = RedLockController.GetConnection().CreateLock(lockKey, expiry);
}
public void Dispose()
{
Lock?.Dispose();
}
}
给出以下 class:
public sealed class DistributedLock : IDisposable
{
private IRedLock Lock { get; }
private bool _disposed;
public DistributedLock(string lockKey, TimeSpan expiry)
{
Lock = RedLockController.GetConnection().CreateLock(lockKey, expiry);
}
private void Dispose(bool disposing)
{
if (_disposed)
return;
if (disposing)
{
if (Lock != null)
{
Lock.Dispose();
}
}
_disposed = true;
}
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
~DistributedLock()
{
Dispose(false);
}
}
其中IRedLock
实现了iDisposable
,而我上面的class的使用方式如下:
using(new DistributedLock("SomeKey"))
{
... do something
}
DistributedLock
和包含的 IRedLock
class 在任何情况下都会从内存中释放吗?
IDisposable
是关于管理除内存以外的资源:比如 GDI 句柄、套接字、文件句柄等。它不会抢占垃圾收集器。所以,IDisposable
只会在两种情况下帮你释放内存:
- 如果您的
IRedLock
类型需要 unmanaged 内存,例如通过第三方库或unsafe
代码。 - 如果您的
Dispose()
方法从其他对象中清除对该对象的引用,以确保该对象有资格进行垃圾回收,否则可能不会(例如,事件处理程序)。
如果这两者都不适用(并且上面的代码中没有任何内容表明它们适用),那么就内存管理而言,您不会从 IDisposable
中获得任何好处。
您可能会从这段代码中的 IDisposable
中获得一种更好的机制来释放此行中提示的连接:
Lock = RedLockController.GetConnection().CreateLock(lockKey, expiry);
但是,您可能不需要关联的终结器。您只是包装了已经具有终结器的其他东西,因此您可以使用更简单的 IDisposable 模式而不会增加额外的复杂性:
public sealed class DistributedLock : IDisposable
{
private IRedLock Lock { get; }
public DistributedLock(string lockKey, TimeSpan expiry)
{
Lock = RedLockController.GetConnection().CreateLock(lockKey, expiry);
}
public void Dispose()
{
Lock?.Dispose();
}
}