一直以来在 VB6 下,参数默认都是按照 ByRef 传送的,(即按地址传送)
而在 .Net(C# Ref,out ) 下, 参数默认是使用 ByVal (即按值传送) 传送的,变量的复本被传递.
按地址传送参数是否会比 按值传递 更快呢,我进行了以下测试,分别对 以下3种对象
DataTable ,Array ,String 进行了测试
测试中为了避免变量在循环中被缓存,每个循环传递的变量都是不同的
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
Dim II As Int32
Dim JJ As Int32
Dim KK As Int32
Dim t As Long
Dim d1 As New DataTable
Dim d2 As New DataTable
Dim r As DataRow
Dim a(4) As Int64
d1.Columns.Add("col1")
d1.Columns.Add("col2")
d1.Columns.Add("col3")
d1.Columns.Add("col4")
d1.Columns.Add("col5")
d1.Columns.Add("col6")
d2.Columns.Add("col1")
d2.Columns.Add("col2")
d2.Columns.Add("col3")
d2.Columns.Add("col4")
d2.Columns.Add("col5")
d2.Columns.Add("col6")
t = Now.Ticks
d1.Rows.Clear()
For KK = 1 To 10000
For II = 1 To 5
r = d1.NewRow
For JJ = 0 To 4
r(JJ) = CStr(II.ToString & JJ.ToString).ToString & KK.ToString
Next
d1.Rows.Add(r)
Next
TestDataTableByVal(d1)
Next
MsgBox("DataTable ByVal: " & CStr((Now.Ticks - t) / 10000)).ToString()
t = Now.Ticks
d2.Rows.Clear()
For KK = 1 To 10000
For II = 1 To 5
r = d2.NewRow
For JJ = 0 To 4
r(JJ) = CStr(II.ToString & JJ.ToString).ToString & KK.ToString
Next
d2.Rows.Add(r)
Next
TestDataTableByRef(d2)
Next
MsgBox("DataTable Byref : " & CStr((Now.Ticks - t) / 10000)).ToString()
t = Now.Ticks
For KK = 1 To 100000
Dim s As String
s = KK.ToString & "123456789012345678901234567890"
TestStringByVal(s)
Next
MsgBox("String byval:" & CStr((Now.Ticks - t) / 10000)).ToString()
t = Now.Ticks
For KK = 1 To 100000
Dim s As String
s = KK.ToString & "123456789012345678901234567890"
TestStringByRef(s)
Next
MsgBox("String byref :" & CStr((Now.Ticks - t) / 10000)).ToString()
t = Now.Ticks
For KK = 1 To 100000
For II = 0 To 4
a(II) = Now.Ticks
Next
TestArrayByVal(a)
Next
MsgBox("Array byval :" & CStr((Now.Ticks - t) / 10000)).ToString()
t = Now.Ticks
For KK = 1 To 100000
For II = 0 To 4
a(II) = Now.Ticks
Next
TestArrayByRef(a)
Next
MsgBox("Array byref :" & CStr((Now.Ticks - t) / 10000)).ToString()
End Sub
Private Sub TestDataTableByVal(ByVal d As DataTable)
Dim s As String
Dim II As Int32
With d.Rows(0)
For II = 0 To 4
s = .Item(II).ToString
Next
End With
End Sub
Private Sub TestDataTableByRef(ByRef d As DataTable)
Dim s As String
Dim II As Int32
With d.Rows(0)
For II = 0 To 4
s = .Item(II).ToString
Next
End With
End Sub
Private Sub TestStringByVal(ByVal d As String)
Dim s As String
s = d
End Sub
Private Sub TestStringByRef(ByRef d As String)
Dim s As String
s = d
End Sub
Private Sub TestArrayByVal(ByVal a As Array)
Dim d As Array
d = a
End Sub
Private Sub TestArrayByRef(ByRef a As Array)
Dim d As Array
d = a
End Sub
测试结果: (每次重新启动软件)
第1次 |
|
|
|
|
DataTable |
String |
Array |
ByVal |
2687.5 |
125 |
140.625 |
ByRef |
2906.25 |
93.75 |
125 |
第2次 |
|
|
|
|
DataTable |
String |
Array |
ByVal |
2734.375 |
156.25 |
140.625 |
ByRef |
2828.125 |
109.375 |
125 |
第3次 |
|
|
|
|
DataTable |
String |
Array |
ByVal |
2687.5 |
171.875 |
125 |
ByRef |
2687.5 |
93.75 |
125 |
第4次 |
|
|
|
|
DataTable |
String |
Array |
ByVal |
2687.5 |
171.875 |
140.625 |
ByRef |
2781.25 |
93.75 |
125 |
第5次 |
|
|
|
|
DataTable |
String |
Array |
ByVal |
2703.125 |
156.25 |
140.625 |
ByRef |
2828.125 |
109.375 |
125 |
String 在使用byref 传递时要比 Byval 快
而复杂的对象 即对象模型较多层的 则 byVal 比 Byref 快一点
数组 传递差别不大