Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/string/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Vb.net Net将哈希表和字符串传递给递归过程_Vb.net_String_Recursion_Hashtable - Fatal编程技术网

Vb.net Net将哈希表和字符串传递给递归过程

Vb.net Net将哈希表和字符串传递给递归过程,vb.net,string,recursion,hashtable,Vb.net,String,Recursion,Hashtable,这里我有一个递归程序。似乎每当哈希表被传递到递归过程(ByVal或ByRef)时,即使退出该过程,它也会留在内存中。该字符串在每次调用过程时都会保留在内存中,但在退出过程时会消失,因为它是通过ByVal传递的。这两个物体是被区别对待的,还是我的理解有偏差 在form1_load的末尾,为什么ht.count总是等于4,而不管它是通过byref还是byval传递的 我认为ht.count和str的长度应该始终相同,因为两者都是通过val传递的。为什么不是这样 谢谢你的帮助和理解!如果我需要说得更清

这里我有一个递归程序。似乎每当
哈希表
被传递到递归过程(
ByVal
ByRef
)时,即使退出该过程,它也会留在内存中。该字符串在每次调用过程时都会保留在内存中,但在退出过程时会消失,因为它是通过
ByVal
传递的。这两个物体是被区别对待的,还是我的理解有偏差

form1_load
的末尾,为什么ht.count总是等于4,而不管它是通过byref还是byval传递的

我认为ht.count和str的长度应该始终相同,因为两者都是通过val传递的。为什么不是这样

谢谢你的帮助和理解!如果我需要说得更清楚,请告诉我

Private Sub Form1_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
    Dim ht As New Hashtable
    Dim i As Integer = 1
    Dim str As String = ""
    go(ht, str, i)
    MsgBox("strLen = " & Len(str) & vbCrLf & "htCount = " & ht.Count)
End Sub
Private Sub go(ByVal ht As Hashtable, ByVal str As String, ByVal i As Integer)

    str = str & "0"
    ht.Add(i, 0)

    i = i + 1
    If i < 5 Then
        go(ht, str, i)
    End If

End Sub
Private Sub Form1\u Load(ByVal sender作为对象,ByVal e作为System.EventArgs)处理Me.Load
Dim ht作为新哈希表
尺寸i为整数=1
Dim str As String=“”
go(ht、str、i)
MsgBox(“strLen=”&Len(str)&vbCrLf&“htCount=”&ht.Count)
端接头
私有子go(ByVal ht作为哈希表,ByVal str作为字符串,ByVal i作为整数)
str=str&“0”
ht.Add(i,0)
i=i+1
如果我小于5,那么
go(ht、str、i)
如果结束
端接头
编辑:我不能回答我自己的问题,因为我是新来的,所以我也意识到:

对于任何想知道的人,我意识到我试图理解可变对象传递给过程byref或byval的方式。我添加了ht2,现在go过程只是将ht分配给ht2

Private Sub Form1_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
    Dim ht As New Hashtable
    Dim ht2 As New Hashtable
    Dim i As Integer = 1
    Dim str As String = ""
    go(ht, str, i, ht2)
    MsgBox("strLen = " & Len(str) & vbCrLf & "htCount = " & ht.Count & vbCrLf & "ht2Count = " & ht2.Count)
End Sub
Private Sub go(ByVal ht As Hashtable, ByVal str As String, ByVal i As Integer, ByVal ht2 As Hashtable)

    str = str & "0"
    ht.Add(i, 0)
    ht2 = ht

    i = i + 1
    If i < 5 Then
        go(ht, str, i, ht2)
    End If

End Sub
Private Sub Form1\u Load(ByVal sender作为对象,ByVal e作为System.EventArgs)处理Me.Load
Dim ht作为新哈希表
Dim ht2作为新哈希表
尺寸i为整数=1
Dim str As String=“”
go(ht、str、i、ht2)
MsgBox(“strLen=“&Len(str)&vbCrLf&”htCount=“&ht.Count&vbCrLf&”ht2Count=“&ht2.Count”)
端接头
私有子go(ByVal ht作为哈希表,ByVal str作为字符串,ByVal i作为整数,ByVal ht2作为哈希表)
str=str&“0”
ht.Add(i,0)
ht2=ht
i=i+1
如果我小于5,那么
go(ht、str、i、ht2)
如果结束
端接头

现在ht2依赖于它传递给过程的方式,ht2.count应该始终与str的长度相同。这也帮助我理解:

String
s和
哈希表
s都是引用类型。您的案例中的主要区别在于它们的可变性

String
s是不可变的。每当您“编辑”一个
字符串时,您都在堆上的一个新内存位置创建一个新的字符串


HashTable
s是可变的,因此当您添加/删除一个元素时,您并不是在构建一个全新的
HashTable
。它保持在堆上以前的位置。

这两个对象没有区别对待。问题是你如何使用它们。字符串连接不会更改字符串,它只返回一个带有连接值的新字符串。但是,Hashtable.Add()会更改对象

ByRef的事情更难理解。字符串的ByRef的行为与预期的一样,因为您正在更改所引用的对象。但是,哈希表的ByRef的行为与您期望的不一样,因为您正在向该表发送消息。Add告诉该表:将其添加到集合中。因此,您总是处理同一个对象


因此,这里的区别在于,您正在创建字符串的多个副本并更改引用,但您只有一个哈希表副本并更改其内容。

谢谢!这使我走上了正确的道路。我意识到我试图将哈希表的易变性与它传递给过程的方式联系起来。谢谢!这就是我需要的。另外,我刚刚意识到,如果我希望哈希表的返回依赖于它传递给过程的方式,那么我应该在递归函数中构建一个新的哈希表,并返回这个新的哈希表。