洗牌2D卡阵列

时间:2015-05-11 09:29:04

标签: c# arrays

我有一个二维的“卡片”数组,我需要在行和列中混洗这个数组。

我的数组是这样的:

private CardType[,] card =
{
    {CardType.Basic, CardType.Basic2, CardType.Basic4 },
    {CardType.Basic, CardType.Basic2, CardType.Basic30 },
    {CardType.Basic, CardType.Basic10, CardType.Basic5 },
    {CardType.Basic, CardType.Basic20, CardType.Basic30 },
};

我需要一种方法来在行和列中混洗卡阵列。

3 个答案:

答案 0 :(得分:2)

使用Fisher-Yates算法:

public static void Shuffle<T>(Random random, T[,] array)
{
    int lengthRow = array.GetLength(1);

    for (int i = array.Length - 1; i > 0; i--)
    {
        int i0 = i / lengthRow;
        int i1 = i % lengthRow;

        int j = random.Next(i + 1);
        int j0 = j / lengthRow;
        int j1 = j % lengthRow;

        T temp = array[i0, i1];
        array[i0, i1] = array[j0, j1];
        array[j0, j1] = temp;
    }
}

使用示例:

CardType[,] cards =
{
    { CardType.Basic, CardType.Basic2, CardType.Basic4 },
    { CardType.Basic, CardType.Basic2, CardType.Basic30 },
    { CardType.Basic, CardType.Basic10, CardType.Basic5 },
    { CardType.Basic, CardType.Basic20, CardType.Basic30 },
};

Random rnd = new Random();
Shuffle(rnd, cards);

请注意,您应该尝试重用rnd,而不是重新创建它!

请注意array.Length如何是数组的总Length,X * Y,以及我们在i中将其分割为“全局索引”i0的方式, i1xy)将模数除以“行”(lengthRow)的长度。

答案 1 :(得分:1)

使用class Random生成源行和dest行,source-col和dest-col。

交换这两个元素(如果不相同)

经常这样做。

答案 2 :(得分:1)

您可以使用标准shuffle来执行此操作。您只需要将单个索引转换为行/列值,如下所示:

/// <summary>Used to shuffle collections.</summary>

public class Shuffler
{
    public Shuffler()
    {
        _rng = new Random();
    }

    /// <summary>Creates the shuffler with a specific random number generator.</summary>

    public Shuffler(Random rng)
    {
        _rng = rng;
    }

    /// <summary>Shuffles the specified array.</summary>

    public void Shuffle<T>(IList<T> array)
    {
        for (int n = array.Count; n > 1; )
        {
            int k = _rng.Next(n);
            --n;
            T temp = array[n];
            array[n] = array[k];
            array[k] = temp;
        }
    }

    /// <summary>Shuffles the specified 2D array.</summary>

    public void Shuffle<T>(T[,] array)
    {
        int w = array.GetUpperBound(1)+1;

        for (int n = array.Length; n > 1; )
        {
            int k = _rng.Next(n);
            --n;

            int dr = n/w;
            int dc = n%w;
            int sr = k/w;
            int sc = k%w;

            T temp = array[dr,dc];
            array[dr,dc] = array[sr,sc];
            array[sr,sc] = temp;
        }
    }

    private readonly Random _rng;
}

您可以像这样使用它:

int[,] array = new int[5, 7];
int w = array.GetUpperBound(1)+1;

// Fill array with 0, 1, 2, ... , 5*7-1

for (int i = 0; i < array.Length; ++i)
{
    int sr = i/w;
    int sc = i%w;

    array[sr, sc] = i;
}

var shuffler = new Shuffler();
shuffler.Shuffle(array);

Console.WriteLine(array[0,0]);