在2D数组中重复排列的列表

时间:2017-06-22 01:09:31

标签: java recursion multidimensional-array permutation repeat

我有一个问题是列出重复的排列,保持这种“风格”,使用递归函数。

在2D数组中有例如2个元素“AB”和“CD”:

Element[0][0] = A; Element[0][1] = B; // AB    
Element[1][0] = C; Element[1][1] = D; // CD

我想通过重复n个元素(在本例中为2)将所有可能的排列组合成k个组(在本例中为2)并将它们保存到新的2D数组中 例如:

Permutation[0][0] = AB; Permutation[0][1] = AB; // 1°: AB,AB
Permutation[1][0] = AB; Permutation[1][1] = CD; // 2°: AB,CD
Permutation[2][0] = CD; Permutation[2][1] = AB; // 3°: CD,AB
Permutation[3][0] = CD; Permutation[3][1] = CD; // 4°: CD,CD

元素和置换必须是二维数组。 我尝试过这种方式,但它只能将2个元素的排列分成两组并且我被锁定了:

    int i_perm = 0;
    int i_element = 0;
    int k_tot = 2; // number of groups

    [...]

    calcPerms(2);

    [...]

    private void calcPerms(int k)
    {
        if (k == 0)
        {
            if(i_perm + 1 < i_perm)
                i_perm++;

            i_element=0;
        }
        else
        {
            for (int i = 0; i < element.length; i++)
            {
                Permutation[i_perm][i_element][0] = Element[i][0];
                Permutation[i_perm][i_element][1] = Element[i][1];

                if(i_element + 1 < k_tot)
                    i_element++;

                calcPerms(k - 1);

                if(i_perm >= i_perm)
                    i_perm--;

                Permutation[i_perm][i_element][0] = Element[i][0];
                Permutation[i_perm][i_element][1] = Element[i][1];
                if(i_element + 1 < k_tot)
                    i_element++;
            }
        }
    }

如上所述,这只适用于2个组中2个元素的排列,正确返回:

ABAB,ABCD,CDAB,CDCD。

确实如果我放3个元素(第3个元素是EF),它会返回:

ABAB,ABCD,CDEF,EFAB,ABCD,CDEF,EFAB,ABCD,EFEF

而不是:

ABAB,ABCD,ABEF,CDAB,CDCD,CDEF,EFAB,EFCD,EFEF

我怎样才能得到我想要的东西?谢谢大家的帮助,并为我糟糕的英语道歉

1 个答案:

答案 0 :(得分:0)

您需要的是Heap's Algorithm

在链接的维基百科页面中有一个清晰的伪代码实现。

非递归版本看起来像这样

procedure generate(n : integer, A : array of any):
    c : array of int

    for i := 0; i < n; i += 1 do
        c[i] := 0
    end for

    output(A)

    i := 0;
    while i < n do
        if  c[i] < i then
            if i is even then
                swap(A[0], A[i])
            else
                swap(A[c[i]], A[i])
            end if
            output(A)
            c[i] += 1
            i := 0
        else
            c[i] := 0
            i += 1
        end if
    end while