2016-05-18 73 views
0

我正在运行一个Permute函数,但是我遇到类似这样的结果的问题,如何防止这种情况发生?在Permute函数中重复的问题

red|red|white 
white|red|red 

Public buffer As New List(Of String) 
Public Sub Permute(ByVal Root As String, ByVal Depth As Integer, ByVal Buffer1 As List(Of String)) 
    Dim data_array As String() = {"red", "blue", "white"} 
    For Each myStr As String In data_array 
     If Depth <= 1 Then 
      Buffer1.Add(Root & myStr) 
     Else 
      Permute(Root & myStr & ",", Depth - 1, Buffer1) 
     End If 
    Next 
End Sub 

回答

1

Bjørn-Roger Kringsjå做此繁重在this great answer一些C++代码转换为VB。

原始作品用于排列字符串字符。我修改它以使用字符串(我一直在做的事),并允许您指定分隔符。您可以返回一个List(Of String())或类似的号码,并使用String.Join来自调用代码。

Public NotInheritable Class Permutation 

    Public Shared Function Create(array As String(), sep As String) As List(Of String) 
     Return Permutation.Create(array, False, sep) 
    End Function 

    Public Shared Function Create(array As String(), sort As Boolean, 
            sep As String) As List(Of String) 
     If (array Is Nothing) Then 
      Throw New ArgumentNullException("array") 
     ElseIf ((array.Length < 0) OrElse (array.Length > 13)) Then 
      Throw New ArgumentOutOfRangeException("array") 
     End If 
     Dim list As New List(Of String) 
     Dim n As Integer = array.Length 
     Permutation.Permute(list, array, 0, array.Length, sep) 
     If (sort) Then 
      list.Sort() 
     End If 
     Return list 
    End Function 

    Private Shared Sub Permute(list As List(Of String), array As String(), 
           start As Int32, ndx As Int32, sep As String) 
     Permutation.Print(list, array, ndx, sep) 
     If (start < ndx) Then 
      Dim i, j As Integer 
      For i = (ndx - 2) To start Step -1 
       For j = (i + 1) To (ndx - 1) 
        Permutation.Swap(array, i, j) 
        Permutation.Permute(list, array, (i + 1), ndx, sep) 
       Next 
       Permutation.RotateLeft(array, i, ndx) 
      Next 
     End If 
    End Sub 

    Private Shared Sub Print(list As List(Of String), array As String(), 
          size As Int32, sep As String) 
     Dim tmp As New List(Of String) 
     If (array.Length <> 0) Then 
      For i As Integer = 0 To (size - 1) 
       tmp.Add(array(i)) 
      Next 
      list.Add(String.Join(sep, tmp)) 
     End If 
    End Sub 

    Private Shared Sub Swap(array As String(), i As Int32, j As Int32) 
     Dim tmp As String 
     tmp = array(i) 
     array(i) = array(j) 
     array(j) = tmp 
    End Sub 

    Private Shared Sub RotateLeft(array As String(), start As Int32, n As Int32) 
     Dim tmp As String = array(start) 
     For i As Integer = start To (n - 2) 
      array(i) = array(i + 1) 
     Next 
     array(n - 1) = tmp 
    End Sub 
End Class 

注意:我的mods将与Kringsjå先生的原始代码很好地共存为重载。用法:

Dim data = {"red", "blue", "white"} 

Dim combos = Permutation.Create(data, ", ") 

结果:

红色,蓝色,白色
红,白,蓝
蓝色,红色,白色
蓝,白,红
白色,红色,蓝色
白色,蓝色,红色

0

Wha你正在做的是选择{ "red", "blue", "white" }Depth次之一。所以,如果你叫Permute("", 5, buffer)你会得到如下:

 
red,red,red,red,red 
red,red,red,red,blue 
... 
white,white,white,white,blue 
white,white,white,white,white 

这3到5个选项的力量。

如果你只想得到{ "red", "blue", "white" }所有可能的排列,然后做到这一点:

Public Function Permute(ByVal data As IEnumerable(Of String)) As IEnumerable(Of String) 
    If data.Skip(1).Any() Then 
     Return data.SelectMany(_ 
      Function (x) Permute(data.Except({ x })).Select(_ 
       Function (y) x & "," & y)) 
    Else 
     Return data 
    End If 
End Function 

...并调用它像这样:

Dim results = Permute({ "red", "blue", "white" }) 

我得到的结果是:

 
red,blue,white 
red,white,blue 
blue,red,white 
blue,white,red 
white,red,blue 
white,blue,red 

这将是微不足道的,然后预先Root价值e对这些结果。