深入理解类的垃圾回收、常量属性方法及事件机制
发布时间: 2025-08-17 00:31:31 阅读量: 1 订阅数: 6 

### 深入理解类的垃圾回收、常量属性方法及事件机制
#### 1. 垃圾回收机制
垃圾回收器在程序运行中起着至关重要的作用,它会对堆中的对象进行压缩,并更新程序的引用,以便程序能找到移动后的对象。同时,它还会更新堆,使程序能够从空闲部分分配内存。
当销毁一个对象时,垃圾回收器会释放该对象的内存以及其所包含的任何托管资源,但对于非托管资源,它可能无法释放。我们可以通过`Finalize`和`Dispose`方法来控制对象释放其托管和非托管资源的时间和方式。
##### 1.1 Finalize 方法
垃圾回收器在销毁对象时,会释放对象使用的托管资源。例如,若一个未使用的对象包含一个打开的文件流引用,当垃圾回收器运行时,它会发现该文件流对程序不可访问,从而销毁文件流及其引用对象。
然而,对于 Visual Basic 无法理解的非托管资源,如文件句柄、网络连接或硬件设备通道等,垃圾回收器不知道如何释放这些资源。这时,我们可以通过重写从`Object`类继承的`Finalize`方法来告诉垃圾回收器该怎么做。
垃圾回收器在将对象从堆中永久移除之前会调用其`Finalize`方法,但无法保证调用该方法的具体时间和不同对象`Finalize`方法的调用顺序。
以下是一个示例代码,展示了`Finalize`方法的使用:
```vb
Public Class Form1
Public Running As Boolean
Private Class Junk
Public MyForm As Form1
Public Sub New(my_form As Form1)
MyForm = my_form
End Sub
' Garbage collection started.
Protected Overrides Sub Finalize()
' Stop making objects.
MyForm.Running = False
End Sub
End Class
' Make objects until garbage collection starts.
Private Sub btnCreateObjects_Click() Handles btnCreateObjects.Click
Running = True
Dim new_obj As Junk
Dim max_i As Long
For i As Long = 1 To 1000000
new_obj = New Junk(Me)
If Not Running Then
max_i = i
Exit For
End If
Next i
MessageBox.Show("Allocated " & max_i.ToString & " objects")
End Sub
End Class
```
在这个示例中,`Form1`类定义了公共变量`Running`,`Junk`类包含一个指向`Form1`类的变量。当用户点击“Create Objects”按钮时,程序开始创建`Junk`对象,直到垃圾回收开始。当垃圾回收器销毁一个`Junk`对象时,其`Finalize`方法会将`Form1`对象的`Running`值设为`False`,从而停止创建对象。
另外,当程序结束时,Visual Basic 也会调用每个对象的`Finalize`方法,但同样无法保证调用的具体时间和顺序。
##### 1.2 内存管理建议
对于分配了非托管资源的类,最好尽快使用并释放这些资源,而不是等待`Finalize`方法来处理。因为非托管资源如果不及时正确释放,可能会导致奇怪的行为和内存泄漏。
##### 1.3 Dispose 方法
由于 Visual Basic 无法实时跟踪对象是否可达,因此在程序结束或垃圾回收器回收对象之前,它不知道何时可以永久销毁对象。这意味着对象的内存和资源可能会闲置一段时间。
为了避免这种情况,我们可以使用`Dispose`方法来显式释放对象的资源。一个类应该在其`Finalize`方法中释放任何未管理的资源,并且要确保`Dispose`和`Finalize`方法可以安全地执行多次。
Visual Basic 定义了`IDisposable`接口,方便我们创建`Dispose`方法。以下是一个示例代码:
```vb
Public Class Form1
Private Class Named
Implements IDisposable
' Save our name.
Public Name As String
Public Sub New(new_name As String)
Name = new_name
End Sub
' Free resources.
Protected Overrides Sub Finalize()
Dispose()
End Sub
' Display our name.
Public Sub Dispose() Implements System.IDisposable.Dispose
Static done_before As Boolean = False
If done_before Then Exit Sub
done_before = True
Debug.WriteLine(Name)
End Sub
End Class
' Make an object and dispose it.
Private Sub btnDispose_Click() Handles btnDispose.Click
Static i As Integer = 0
i += 1
Dim obj As New Named("Dispose " & i)
obj.Dispose()
End Sub
' Make an object and do not dispose it.
Private Sub btnNoDispose_Click() Handles btnNoDispose.Click
Static i As Integer = 0
i += 1
Dim obj As New Named("No Dispose " & i)
End Sub
End Class
```
在这个示例中,`Named`类实现了`IDisposable`接口,其`Finalize`方法调用`Dispose`方法。`Dispose`方法使用静态变量`done_before`确保只执行一次。当点击“Dispose”按钮时,程序创建一个`Named`对象并调用其`Dispose`方法;当点击“No Dispose”按钮时,程序创建对
0
0
相关推荐










