5

C#でカードトリックゲームを作りたいです。カード(裏面)となるフォームのピクチャーボックスをデザインしました。また、0 から 51 までの乱数を作成し、その数値を使用して ImageList から画像を設定する各画像の Click メソッドも作成しました。

        Random random = new Random();
        int i = random.Next(0, 51);
        pictureBox1.Image = imageList1.Images[i];

私の問題は、時々同じ数字 (例: スペードのジャック 2 つ) を取得することです。どうすればそれを防ぐことができますか? (つまり、たとえば、(5)を取得した場合、別の(5)を取得する可能性があります)

4

4 に答える 4

5

すでに選択した番号を にHashSet<int>保存し、現在の番号が になくなるまで選択を続けHashSetます。

// private HashSet<int> seen = new HashSet<int>();
// private Random random = new Random(); 

if (seen.Count == imageList1.Images.Count)
{
    // no cards left...
}

int card = random.Next(0, imageList1.Images.Count);
while (!seen.Add(card))
{
    card = random.Next(0, imageList1.Images.Count);
}

pictureBox1.Image = imageList1.Images[card];

または、多数の数値を選択する必要がある場合は、配列に連続した数値を入力し、各インデックスの数値を別のランダム インデックスの数値と交換できます。次に、ランダム化された配列から上位 N 個の必要なアイテムを取得します。

于 2013-05-19T17:09:41.783 に答える
5

繰り返し画像がないことを確認したい場合は、残りのカードのリストを取得し、表示されているカードを毎回削除できます。

Random random = new Random();    
List<int> remainingCards = new List<int>();

public void SetUp()
{
    for(int i = 0; i < 52; i++)
        remainingCards.Add(i);
}

public void SetRandomImage()
{
   int i = random.Next(0, remainingCards.Count);
   pictureBox1.Image = imageList1.Images[remainingCards[i]];
   remainingCards.RemoveAt(i);
} 
于 2013-05-19T17:10:28.363 に答える
2

52 枚のカードの配列を作成します。配列をシャッフルし (たとえば、高速な Fisher-Yates shuffleを使用)、新しいカードが必要なときに反復します。

int[] cards = new int[52]; 

//fill the array with values from 0 to 51 
for(int i = 0; i < cards.Length; i++)
{
    cards[i] = i;
}

int currentCard = 0;

Shuffle(cards);

//your cards are now randomised. You can iterate over them incrementally, 
//no need for a random select
pictureBox1.Image = imageList1.Images[currentCard];
currentCard++;


public static void Shuffle<T>(T[] array)
{
    var random = _random;
    for (int i = array.Length; i > 1; i--)
    {
        // Pick random element to swap.
        int j = random.Next(i); // 0 <= j <= i-1
        // Swap.
        T tmp = array[j];
        array[j] = array[i - 1];
        array[i - 1] = tmp;
    }
}

基本的に、実際のゲームと同じように、デッキをシャッフルして、毎回一番上のカードを取るだけです。毎回ランダムなインデックスを常に選択する必要はありません。

于 2013-05-19T17:06:19.363 に答える
1

私が今まで使った簡単なトリックを使ってもいいと思います。2 つのランダム インデックス間で画像を 50 回交換します。少ないか多いと、より多くのランダムが得られます。これは@faesterの答えと似ているかもしれません。

于 2013-05-19T17:12:39.207 に答える