Пример утечки памяти в .NET из-за обработчиков событий, пожалуйста?

Тут и там люди продолжают говорить об утечках памяти, которые происходят из-за невыпущенных прослушивателей событий. Я думаю, что это очень важная проблема. Очень серьезная и очень важная... если она действительно существует.

Я пытался сам воспроизвести проблему, но все мои попытки не увенчались успехом: я просто не могу сделать мое приложение утечкой памяти :( Хотя это звучит хорошо, я все еще беспокоюсь: может быть, я что-то упускаю.

Может быть, кто-нибудь может предоставить очень простой пример исходного кода, вызывающий утечку памяти?

В качестве демонстрации я создал небольшое приложение VB.NET: оно содержит одну форму Windows и один класс.

Форма Windows: имеет объект коллекции (с именем «c») и две кнопки: одну для добавления 10 элементов в коллекцию и другую для очистки коллекции:

Public Class Form1

Dim c As New Collection

Private Sub btnAddItem_Click(sender As System.Object, e As System.EventArgs) Handles btnAddItem.Click
    For i As Integer = 1 To 10
        Dim m As New MyType
        c.Add(m)
    Next

    Me.Text = c.Count
End Sub

Private Sub btnClear_Click(sender As System.Object, e As System.EventArgs) Handles btnClear.Click
    For Each item As MyType In c
        item.Dispose()
    Next
    c.Clear()

    Me.Text = c.Count
End Sub
End Class

Класс MyType: имеет большой объект m_Image, который большой, чтобы вы могли видеть, что ваша память действительно занята экземплярами MyType :)

Imports System.Drawing

Public Class MyType 
Implements IDisposable

Private m_Image As Bitmap

Public Sub New()
    AddHandler Application.Idle, AddressOf Application_Idle

    m_Image = New Bitmap(1024, 1024)
End Sub

Private Sub Application_Idle(sender As Object, e As EventArgs)

End Sub

#Region "IDisposable Support"
Private disposedValue As Boolean

Protected Overridable Sub Dispose(disposing As Boolean)
    If Not Me.disposedValue Then
        If disposing Then
            m_Image.Dispose()
        End If
    End If
    Me.disposedValue = True
End Sub

Public Sub Dispose() Implements IDisposable.Dispose
    Dispose(True)
    GC.SuppressFinalize(Me)
End Sub
#End Region

End Class
5
задан Dima 7 April 2012 в 17:16
поделиться