VB.NET - 实现 IDisposable 时是否应该添加 Finalize 方法?
在 Visual Studio 中,当我键入“Implements IDisposable
”行时,IDE 会自动添加:
disposeValue
成员变量Sub Dispose() Implements IDisposable.Dispose< /code>
- a
Sub Dispose(ByVal disusing As Boolean)
应该保留 Dispose()
,清理代码应该放在 Dispose(disusing )
。
但是 Dispose Finalize Pattern 表示您应该还重写 Sub Finalize()
以调用 Dispose(False)
。 为什么IDE不添加这个呢? 我必须自己添加它,还是以某种方式隐式调用它?
编辑:知道为什么 IDE 会自动添加 80% 的必需内容但忽略 Finalize 方法吗? 这种功能的全部意义不就是帮助您不忘记这些事情吗?
编辑2:谢谢大家的出色回答,现在这使得完美的感觉!
In Visual Studio, when I type the line "Implements IDisposable
", the IDE automatically adds:
- a
disposedValue
member variable - a
Sub Dispose() Implements IDisposable.Dispose
- a
Sub Dispose(ByVal disposing As Boolean)
The Dispose()
should be left alone, and the clean up code should be put in Dispose(disposing)
.
However the Dispose Finalize Pattern says you should also override Sub Finalize()
to call Dispose(False)
. Why doesn't the IDE also add this? Must I add it myself, or is it somehow called implicitly?
EDIT: Any idea why the IDE automatically adds 80% of the required stuff but leaves out the Finalize method? Isn't the whole point of this kind of feature to help you not forget these things?
EDIT2: Thank you all for your excellent answers, this now makes perfect sense!
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
如果您实际上持有垃圾收集器不会自动清理的非托管资源并在 Dispose() 中清理它们,那么是的,您应该在 Finalize() 中执行相同的操作。
如果您出于其他原因实现 IDisposable,则不需要实现 Finalize()。
基本问题是:如果没有调用 Dispose() 并且您的对象被垃圾收集,内存会泄漏吗? 如果是,则执行Finalize。 如果没有,则不需要。 另外,避免“仅仅因为它更安全”而实现 Finalize。 具有自定义终结器的对象可能需要两次 GC 传递来释放它们——一次将它们放入挂起的终结器队列,第二次传递实际释放其内存。
If you actually are holding non-managed resources that will not be automatically cleaned up by the garbage collector and cleaning those up in your Dispose(), then yes, you should do the same in Finalize().
If you're implementing IDisposable for some other reason, implementing Finalize() isn't required.
The basic question is this: If Dispose() wasn't called and your object garbage collected, would memory leak? If yes, implement Finalize. If no, you don't need to. Also, avoid implementing Finalize "just because it's safer". Objects with custom finalizers can potentially need two GC passes to free them -- once to put them on the pending finalizers queue, and a second pass to actually free their memory.
不,除非您有非托管资源需要清理,否则您不需要 Finalize。
在大多数情况下,类是一次性的的原因是它保留对其他托管 IDisposable 对象的引用。 在这种情况下,不需要或不需要 Finalize 方法。
No, you don't need to have Finalize unless you have unmanaged resources to clean up.
In most cases the reason a class is disposable is because it keeps references to other managed IDisposable objects. In this case no Finalize method is necessary or desirable.
正如其他人所说,除非您直接持有非托管资源,否则您不需要实现终结器。 另外,假设您使用 .NET 2.0 或更高版本,您不太可能需要实现终结器,因为通常 SafeHandle 可用于包装非托管资源。
我写了一个相当很长的博客文章介绍了 IDisposable 和终结器的背景和实现,如果您不完全清楚它可能值得一读。
As others have said, you don't need to implement a finalizer unless you're directly holding unmanaged resources. Also, assuming you're working in .NET 2.0 or later, it's unlikely you'll ever need to implement a finalizer because typically SafeHandle can be used to wrap your unmanaged resources.
I wrote a fairly long blog post covering the background and implementation of IDisposable and finalizers a while back, which may be worth a read if you're not totally clear about it.