VBA-如何使随机字符串数组起作用?

时间:2018-10-18 04:09:09

标签: vba ms-access access-vba

概述:我将许多行上的单词粘贴到文本框中:txtWordRandomizer。然后,将每一行移动到字符串数组中。我需要对数组进行混洗/随机化,但似乎无法使其正常工作。

我在下面找到了最下面的Sub ShuffleArray():http://www.cpearson.com/excel/ShuffleArray.aspx ...这似乎是每个人在谈论改组/随机化数组时所引用的内容。

我收到错误消息:类型不匹配:在调用ShuffleArrayInPlace()时出现数组或用户定义的类型,但认为这是用于随机化字符串数组。我是否需要将字符串数组转换为变量数组?

或者,关于如何使它工作的其他建议?

    Private Sub btnRandomize_Click()

        Dim strRandoms() As String
        strRandoms() = Split(Me.txtWordRandomizer.Value, vbCrLf)
        strRandoms() = ShuffleArray(strRandoms())

    End Sub    


Function ShuffleArray(InArray() As Variant) As Variant()

' This function returns the values of InArray in random order. The original
' InArray is not modified.

    Dim N As Long
    Dim Temp As Variant
    Dim J As Long
    Dim Arr() As Variant


    Randomize
    L = UBound(InArray) - LBound(InArray) + 1
    ReDim Arr(LBound(InArray) To UBound(InArray))
    For N = LBound(InArray) To UBound(InArray)
        Arr(N) = InArray(N)
    Next N
    For N = LBound(InArray) To UBound(InArray)
        J = CLng(((UBound(InArray) - N) * Rnd) + N)
        Temp = InArray(N)
        InArray(N) = InArray(J)
        InArray(J) = Temp
    Next N
    ShuffleArray = Arr
End Function

2 个答案:

答案 0 :(得分:0)

基于一些快速测试,发布的链接中的ShuffleArray函数实际上并未返回随机数组。由于将数组保留在strRandoms变量中,因此无论如何都可以使用就地函数(就地函数也将更加高效,因为它不必创建和填充全新的函数数组)。

在调用函数并将数组作为参数传递时,不要在数组后加上括号。这样做:

ShuffleArrayInPlace a
' Or this:
Call ShuffleArrayInPlace(a)

但是,为了成功完成此操作,您必须从此处(现在)稍微更改ShuffleArrayInPlace的方法签名:

Sub ShuffleArrayInPlace(InArray() As Variant)

对此:

Sub ShuffleArrayInPlace(InArray As Variant)

请注意,InArray之后的括号已消失。为什么这样

该函数最初带有括号,期望包含Variant值的数组。但是,split函数返回一个 string 值数组。通过更改方法签名以删除括号,您基本上是在说可以将任何东西传递给函数(字符串数组,变体数组,甚至根本不是数组)。因此,如果参数不是数组,则可以更新ShuffleArrayInPlace以引发错误(使用IsArray函数)。

说到重构:尽管ShuffleArrayInPlace用于改组数组的算法很明确,但不一定是最好的算法。我将回顾Fisher-Yates改组,并尝试自己在VBA中实现它作为练习。


所以,总而言之...

  • 在调用将数组作为参数的函数时,请不要在数组后加上括号:`Call ShuffleArrayInPlace(strRandoms)
  • 使用ShuffleArrayInPlace,而不是ShuffleArray
  • 更改ShuffleArrayInPlace函数,以使InArrayVariant,而不是Variant()

答案 1 :(得分:0)

这对我有用:

Private Sub btnRandomize_Click()

    Dim strRandoms() As String
    strRandoms = Split("A|B|C|D|E", "|")
    strRandoms = ShuffleArray(strRandoms)

    Debug.Print Join(strRandoms, ", ")

End Sub


Function ShuffleArray(InArray() As String) As String()
    Dim N As Long, Temp As Variant
    Dim J As Long, Arr() As String

    Randomize

    'make a copy of the array
    ReDim Arr(LBound(InArray) To UBound(InArray))
    For N = LBound(InArray) To UBound(InArray)
        Arr(N) = InArray(N)
    Next N
    'shuffle the copy
    For N = LBound(Arr) To UBound(Arr)
        J = CLng(((UBound(Arr) - N) * Rnd) + N)
        Temp = Arr(N)
        Arr(N) = Arr(J)
        Arr(J) = Temp
    Next N
    ShuffleArray = Arr 'return the shuffled copy
End Function