2012-02-13 7 views
-1

私はC#プログラミングには全く慣れていないので、裸でいます。私はすでにサイトに投稿された多数の質問を読みましたが、同じ問題を抱えるようなものは見えないので、もっと簡単なアプローチができると思います。私のクイズの質問のランダムな注文を作成する

私はクイズアプリケーションを作成し、switch文を使用して質問を処理していました。すなわち1から2、3から4などとなる。 しかし、ユーザーがクイズを一度完了してからもう一度やり直したい場合は、同じ質問を何度も繰り返す必要があります。 (設計が間違っていると、アプリケーションが終了するということです)。 したがって、私はQuestionCountの番号を無作為に(ただし、この番号が1回だけ生成されているか)ランダム化する方法があるかどうかを確認したかったのです。 リストを使用する際の提案がありますが、これらはリストに含まれている多数のものに集中しているようですが、私のものは現在20個の質問にしかなりません。

私は現在使用しているコードをコピーしました。

private void Verify(int Question) 
{ 
    switch (Question) 
    { 
     case 1: 
      if (checkBox1.Checked && !checkBox2.Checked && !checkBox3.Checked && !checkBox4.Checked) 
      { 
       MessageBox.Show("Correct - Well Done"); 
       //This was a test to see if I could assign a random number which works but the number could then appear again meaning the user gets the same question 
       Random random = new Random(); 
       QuestionCount = random.Next(0, 21); 
       QuestionSelection(QuestionCount); 
       //SelectLabel(QuestionCount); 
       ClearcheckBox(); 
      } 
      else 
      { 
       MessageBox.Show("No - It was Sunguard"); 
       Application.Exit(); 
      } 
      break; 
     case 2: 
      if (checkBox3.Checked && !checkBox2.Checked && !checkBox1.Checked && !checkBox4.Checked) 
      { 
       //this method was the original where it just adds 1 to QuestionCount and works it way through the switch statement for the questions. 
       MessageBox.Show("Correct - Well Done"); 
       QuestionCount++; 
       QuestionSelection(QuestionCount); 
       //SelectLabel(QuestionCount); 
       ClearcheckBox(); 
      } 
      else 
      { 
       MessageBox.Show("No - It's to look at a students details"); 
       Application.Exit(); 
      } 
    } 
} 
+0

あなたが探しているキーワードが "シャッフル" です。つまり、置換せずにリストをランダムに並べ替えることです。あなたは質問のリストをシャッフルしたい(あなたのコードでは、質問は 'int'によって識別されるように見えるので、' int'のリスト)。 – perelman

答えて

1

は、なぜあなたはリスト内のすべての質問に入れて、それをシャッフルしないでください:AnsweredQuestionsUnansweredQuestions

public List<T> RandomPermutation<T>(List<T> array) 
{ 
    Random random = new Random(); 
    List<T> retArray = new List<T>(array); 

    int maxIndex = array.Count - 1; 

    for (int i = 0; i <= maxIndex; i++) 
    { 
     int swapIndex = random.Next(i, maxIndex); 
     if (swapIndex != i) 
     { 
      T temp = retArray[i]; 
      retArray[i] = retArray[swapIndex]; 
      retArray[swapIndex] = temp; 
     } 
    } 
    return retArray; 
} 
1

は、私は2つのリストを使用したら、それぞれの質問にだけ尋ねていることを確認するには。

AnsweredQuestionsが空白の場合は、UnansweredQuestionsにすべての質問が含まれています。 これで、すでにあなたのコードの中にあるようなランダマイザーができます。 random.Next()の最大値は、現在CountUnansweredQuestionsリストの項目を取っています。

質問が正しく答えられたら、UnansweredQuestionsのリストから削除してAnsweredQuestionsのリストに入れることができます。

この方法では、あなたのランダム化ツールは本当に未回答の質問のみを使用します。

+0

提案していただきありがとうございます。これは私の質問がswitch文でも保持されている場合でも機能しますか? ます。private void QuestionSelection(int型intQuestionNo) { スイッチ(intQuestionNo) { ケース1: labelQuestion.Text = "バナーを作りました"。 checkBox1。テキスト= "サンガード"; checkBox2.Text = "McDonalds"; checkBox3.Text = "Asda"; checkBox4.Text = "Apple"; 休憩。 これらの質問をcheckbox.textの回答リストに入れようとすると、タスクの権利が判明する可能性がありますか? – jamesc100

+0

申し訳ありませんが、コメントボックスにコードを入れることは素晴らしいことではありません。私は新しいユーザーであるため、別の8時間の新しい投稿を作成することはできません。 – jamesc100

+0

@ user1206484:柔軟性のない質問の数を、たとえば50または1000に変更する必要がある場合、あなたはどうしますか?この方法について:乱数は「UnansweredQuestions」リストの質問のインデックスです。質問はそれぞれの答えと正しい解をプロパティとして提供します。これらのプロパティを適切なチェックボックスに割り当てるメソッドに質問を提供できます。このようにすることで、どれだけ多くの質問をしても決して気にしない柔軟なアプローチができます。 –

0

可能な値の数が少ない場合は、選択肢をUint64のビットフラグとしてエンコードできます。私はそれを行う以下の例を追加しました。

私は便宜上BitArrayを使用します。ビットごとに&と|演算子。 結果は1つのUInt64にパックされますが、フラグと値のための2つの別々のUint32が簡単に作成できました。

private static UInt64 Next(UInt64 current, int questions) 
{ 
    // Convert the current value to an array of bytes. 
    // Remove the least significant 4 bytes. 
    // and then create a flag array. 
    var bytes = BitConverter.GetBytes(current); 
    bytes[0] = bytes[1] = bytes[2] = bytes[3] = 0; 
    var flags = new BitArray(bytes); 

    // If all questions has been answered then exit with 0. 
    var all = Enumerable.Range(32, questions).All(flags.Get); 
    if (all) 
     return 0UL; 

    // Make a random next value, if the value has been used then repeat. 
    var random = new Random(DateTime.Now.Millisecond); 
    var next = random.Next(questions); 
    while (flags.Get(next + 32)) 
     next = random.Next(questions); 

    // set the flag value for the guess. 
    flags.Set(next + 32, true); 

    // convert the flags back to Uint64 and add the next value. 
    flags.CopyTo(bytes, 0); 
    return BitConverter.ToUInt64(bytes, 0) + Convert.ToUInt64(next); 
} 

テストで:

var first = Next(0UL, 20); 
while (first != 0UL) 
{ 
    var v = first & 0xFFFFFFFF; 
    Console.Out.WriteLine(v); 
    first = Next(first, 20); 
}