完全形成处理并释放内存
Totally form Disposing and free up memory
我已经阅读了大量有关 "class disposing" 的主题,我确实了解如何去做,而且效果很好!同时 "form disposind" 不一样,资源还在泄漏!
我在做什么:
正在通过 "using" 方法初始化表单:
Using f as New Form
f.ShowDialog()
'my code
End using
在这种情况下,"end using" 形式以 "Dispose" 方法终止。
例如:
我有一个带有 class 的表单(它包含参数和其他 classes)。
在初始化表单事件时,表单(本身)占用 12Mb 的内存(我在进程资源管理器中对其进行测量),加上我的 class 占用 10Mb(在 Dispose 事件上 Dispose 表单之前是 Disposable 和 Dispose 之前处理的)。在处理完我的表格(我再次测量)后,我看到我的 class 被处理并且资源(class)完全免费,表格没有释放资源。换句话说,我杀死了 10Mb(class)但不要杀死 12Mb(形式)。
我的 Dispose 代码:
Private Sub Form_Disposed(sender As Object, e As EventArgs) Handles
Me.Disposed
If Not fDisposed Then
MyPersonalClass.Dispose()'class
MyPersonalClass = Nothing
fDisposed = True
GC.SuppressFinalize(Me)
GC.Collect()
Finalize()
End If
End Sub
非常糟糕。如果我大部分时间都在使用这些表单,并且如果它们在处理后不释放资源,则每个打开的表单在关闭后将在内存中留下大约 10-12Mb。如果我打开表单 100 次,它会冻结超过 1Gb 的内存。
我做错了什么?
我不太熟悉 VB
,但我认为它会做一些类似于使用 winforms for C#
完成的事情
确保在处置表单时处置 A Form
的所有 Disposable 对象的最简单方法,以保留 Disposable 对象的集合。您可以使用现有的 class Sytem.ComponentModel.Component class for this. The disadvantage is that it only accepts objects that implement interface IComponent。如果你只有几个class必须处理的还没有这个接口,这是最简单的方法。否则设计你自己的DisposableCollection
class DisposableCollection : List<object>, IDisposable
{
public bool IsDisposed {get, private set} = false;
private IEnumerable<IDisposable> DisposableItems => this.OfType<IDisposable>();
public void Dispose()
{
if (!this.IsDisposed)
{
// Dispose all disposable items
foreach (IDisposable disposableItem in this.DisposableItems)
{
disposableItem.Dispose();
}
this.disposed = true;
}
}
}
用法:
class MyForm : Form
{
private readonly DisposableCollection disposables = new DisposableCollection();
public MyForm()
{
// create and add all your items to disposables
}
protected override void OnDisposing(bool disposing)
{
this.disposables.Dispose();
}
}
如果需要,您可以添加事件处理程序以通知其他人该对象正在处理
我已经阅读了大量有关 "class disposing" 的主题,我确实了解如何去做,而且效果很好!同时 "form disposind" 不一样,资源还在泄漏!
我在做什么:
正在通过 "using" 方法初始化表单:
Using f as New Form
f.ShowDialog()
'my code
End using
在这种情况下,"end using" 形式以 "Dispose" 方法终止。
例如:
我有一个带有 class 的表单(它包含参数和其他 classes)。 在初始化表单事件时,表单(本身)占用 12Mb 的内存(我在进程资源管理器中对其进行测量),加上我的 class 占用 10Mb(在 Dispose 事件上 Dispose 表单之前是 Disposable 和 Dispose 之前处理的)。在处理完我的表格(我再次测量)后,我看到我的 class 被处理并且资源(class)完全免费,表格没有释放资源。换句话说,我杀死了 10Mb(class)但不要杀死 12Mb(形式)。
我的 Dispose 代码:
Private Sub Form_Disposed(sender As Object, e As EventArgs) Handles
Me.Disposed
If Not fDisposed Then
MyPersonalClass.Dispose()'class
MyPersonalClass = Nothing
fDisposed = True
GC.SuppressFinalize(Me)
GC.Collect()
Finalize()
End If
End Sub
非常糟糕。如果我大部分时间都在使用这些表单,并且如果它们在处理后不释放资源,则每个打开的表单在关闭后将在内存中留下大约 10-12Mb。如果我打开表单 100 次,它会冻结超过 1Gb 的内存。
我做错了什么?
我不太熟悉 VB
,但我认为它会做一些类似于使用 winforms for C#
确保在处置表单时处置 A Form
的所有 Disposable 对象的最简单方法,以保留 Disposable 对象的集合。您可以使用现有的 class Sytem.ComponentModel.Component class for this. The disadvantage is that it only accepts objects that implement interface IComponent。如果你只有几个class必须处理的还没有这个接口,这是最简单的方法。否则设计你自己的DisposableCollection
class DisposableCollection : List<object>, IDisposable
{
public bool IsDisposed {get, private set} = false;
private IEnumerable<IDisposable> DisposableItems => this.OfType<IDisposable>();
public void Dispose()
{
if (!this.IsDisposed)
{
// Dispose all disposable items
foreach (IDisposable disposableItem in this.DisposableItems)
{
disposableItem.Dispose();
}
this.disposed = true;
}
}
}
用法:
class MyForm : Form
{
private readonly DisposableCollection disposables = new DisposableCollection();
public MyForm()
{
// create and add all your items to disposables
}
protected override void OnDisposing(bool disposing)
{
this.disposables.Dispose();
}
}
如果需要,您可以添加事件处理程序以通知其他人该对象正在处理