2016-10-31 12 views
1

5つの質問をするプログラムを作るにはどうすればいいですか?カウントダウンが0になると
そして、それぞれの質問は、スレッドのスリープ(リターン・カウントダウン)を使用してcoundown 30秒を持って 、それは式を使用してスコアを追加するために次の質問
とどのように進むのだろうか?Java - 簡単な検査方法は?

import java.util.Scanner; 
import java.io.IOException; 

class timer{ 
    public static void main(String[]args) throws IOException{ 
     Scanner scan = new Scanner(System.in); 
     Thread thread1 = Thread.currentThread(); 
     Thread thread2 = new Thread(() -> { 
       try{ 
        for(int seconds = 30; seconds >= 0; seconds--){ 
         System.out.println("\rYou have "+seconds+"second's left!"); 
         Thread.sleep(1000); 
        } 
       }catch(InterruptedException e){} 
      }); 
      System.out.println("What is 1+1? "); 
      System.out.println("a. 1\t b.2\t c.3\t d.4"); 
      thread2.start(); 
      String answer = scan.next(); 
      thread2.stop(); 
    } 
} 
+0

このコンソールアプリケーションですか、またはダイアログウィンドウなどのGUI要素を使用できますか? – Pshemo

+0

何が問題なのですか?あなたのサンプルコードはそのままで、 'Thread.stop()'を使っても安全です。 –

+1

なぜscan.next()ですか?それは常にスレッドを停止し、ユーザーの入力を待つでしょう。このhttp:// stackoverflowもチェックしてください。com/questions/5853989/time-limit-for-input –

答えて

1

私は個人的にawaitsignal/signalAllを使用して、私のスレッドを同期、そして待っている間に答えが与えられたりされなかった場合は知っている方法Condition#await(long time, TimeUnit unit)に頼ってしまうので、私のコードは、そのようなものになるだろう:

Scanner scan = new Scanner(System.in); 
// The lock used to used to synchronize my threads 
Lock lock = new ReentrantLock(); 
// The target condition 
Condition answered = lock.newCondition(); 
Thread thread2 = new Thread(() -> { 
    try { 
     // Indicates whether the question has been answered 
     boolean hasAnswered = false; 
     lock.lock(); 
     try { 
      // Loop until the question has been answered or 10 seconds 
      for (int seconds = 10; !hasAnswered && seconds >= 0; seconds--){ 
       System.out.printf("You have %d sec's left!%n", seconds); 
       // Wait 1 second and if await returns true it means that 
       // I had an answer in time otherwise it means that we 
       // reached the timeout without getting answer 
       hasAnswered = answered.await(1L, TimeUnit.SECONDS); 
      } 
     } finally { 
      lock.unlock(); 
     } 
     // Print the message indication whether we get the answer in time or not 
     if (hasAnswered) { 
      System.out.println("Good Job !!"); 
     } else { 
      System.out.println("Too late !!"); 
     } 
    } catch(InterruptedException e){ 
     Thread.currentThread().interrupt(); 
    } 
}); 
System.out.println("What is 1+1? "); 
System.out.println("a. 1\t b.2\t c.3\t d.4"); 
thread2.start(); 
String answer = scan.next(); 
lock.lock(); 
try { 
    // Notify the other thread that we have an answer 
    answered.signalAll(); // could be answered.signal() as we have only 
          // thread waiting to be notified but it is a 
          // better practice to use signalAll 
} finally { 
    lock.unlock(); 
} 

成功した場合の出力:

What is 1+1? 
a. 1  b.2  c.3  d.4 
You have 10 sec's left! 
You have 9 sec's left! 
You have 8 sec's left! 
You have 7 sec's left! 
2 
Good Job !! 
場合は10

出力は、それは遅すぎる:

What is 1+1? 
a. 1  b.2  c.3  d.4 
You have 10 sec's left! 
You have 9 sec's left! 
You have 8 sec's left! 
You have 7 sec's left! 
You have 6 sec's left! 
You have 5 sec's left! 
You have 4 sec's left! 
You have 3 sec's left! 
You have 2 sec's left! 
You have 1 sec's left! 
You have 0 sec's left! 
Too late !! 
1

私はこのポストはすでにニコラスFilottoの答えのように本当に受け入れ答えと私を持って知っているが、私はちょうどにさらに別の方法があることを共有するだろうと思いました(Javaの場合と同様に)このタスクを実行します。つまり、BufferReader()/ InputStreamReader(System.in)を使用することで、正しく完了した場合にコード操作をブロックせずにコンソールから入力を収集できます。もちろん、追加のスレッドが質問の時間制限メカニズムに使用されます。

しかし、このコードではひどくちょっとしたことがありますが、ユーザーが尋ねられる質問はテキストファイルから取得され、コードと共にテストを使用できます。これにより、テストをハードコードする必要がなくなります。テストテキストファイル内の各行は、パイプ(|)文字で区切られた3つの部分からなる質問です.1番目の部分は質問そのもので、2番目の部分は実際の答えです。オプションの3番目の部分は秒数です3番目の部分に質問がない場合、デフォルトの10秒が使用されます.3番目の部分に0が指定されている場合、質問には時間制限はありません。 :

1: What is: 1 + 1 = ?\n a: 1 b: 2 c: 3 d: 4\n|b|10 
2: What is: 5 + 5 = ?\n a: 1 b: 12 c: 10 d: 15\n|c|20 
3: What is: 6 + 4 = ?\n a: 10 b: 11 c: 12 d: 13\n|a 
4: What is: 2 + 3 = ?\n a: 3 b: 4 c: 5 d: 6\n|c|10 
5: What is: 4 + 3 = ?\n a: 7 b: 6 c: 5 d: 8\n|a|10 

ファイルで見ることができるように内容が3質問は、デフォルトの時間制限を使用しています\ nはトン\タグは、ファイルのテキスト内許可されていると処理タラ内に応じて処理されます。 e。

私はコード操作に掘り下げません。なぜなら、私は何が何をするのかについて非常によくコメントしています。ここには完全な実行可能ファイルがあります:

package timedquestions; 

import java.io.BufferedReader; 
import java.io.File; 
import java.io.FileNotFoundException; 
import java.io.FileReader; 
import java.io.IOException; 
import java.io.InputStreamReader; 
import java.io.LineNumberReader; 
import javax.swing.JDialog; 
import javax.swing.JOptionPane; 

public class TimedQuestions { 
    private static String redColor = "\u001B[31m";  // for setting output text color red 
    private static String blueColor = "\u001B[34m";  // for setting output text color blue 
    private static String purpleColor = "\u001B[35m"; // for setting output text color purple 
    private static String resetColor = "\u001B[39;49m"; // for resetting output text color to default 
    private static boolean questionAnswered = false; // Keeps track of whether a question was answered 
    private static int questionCount = 0;    // Keeps count of number of questions asked to User 
    private static int rightAnswers = 0;    // Keeps count of questions answered Correctly 
    private static int wrongAnswers = 0;    // Keeps count of questions answered Incorrectly 
    private static int defaultSecondsForTimout = 10; // The default question time limit 
    private static int secondsForTimout = 10;   //Current set time limit for question (can change by question) 
    private static boolean timeOut = false;    // Keeps track of whether or not the question has timed out. 


    public static void main(String[] args) { 
     // Start the test... 
     startTest("Test001.txt"); // Your test file path & name goes here. 

     // Calculate and display score for test... 
     double scr = (double) ((rightAnswers/questionCount)*100); 
     int score = (int) Math.ceil((double)rightAnswers/(double)questionCount*100.0); 

     System.out.println("\n======================================================"); 
     System.out.println("Out of a total of " + questionCount + " questions\n" 
         + "you got " + rightAnswers + " questions Correct and\n" 
         + "you got " + wrongAnswers + " questions Wrong.\n" 
         + "Your score is " + + score + "% " 
         + "which gives you a grade of '" + getLetterGrade(score) + "'."); 
     System.out.println("======================================================"); 

     // Done. 
    } 

    private static void startTest(String testFilePath) { 
     // Get the number of lines (questions) within the supplied Test file... 
     int fileLinesCount = 0; 
     LineNumberReader lnr; 
     try { 
      lnr = new LineNumberReader(new FileReader(new File(testFilePath))); 
      lnr.skip(Long.MAX_VALUE); 
      fileLinesCount = (lnr.getLineNumber() + 1); 
      //System.out.println("Within this Test there are " + fileLinesCount + " questions."); 
      lnr.close(); 
     } 
     catch (FileNotFoundException ex) { System.out.println(ex.getMessage()); return; } 
     catch (IOException ex) { System.out.println(ex.getMessage()); return; } 

     // Display test information to the User via a Message Box 
     // and allow User to start the test. 
     String msg = "Within this Test there are " + fileLinesCount + " questions.\n" + 
        "You will have " + secondsForTimout + " seconds to answer each test question.\n" + 
        "If a question runs out of time then you will get that question WRONG.\n\n" + 
        "Press the OK button to start the Test:"; 
     JDialog dialog = new JDialog(); 
     dialog.setAlwaysOnTop(true);  
     JOptionPane.showMessageDialog (dialog, msg, "Test Inforamtion...", JOptionPane.PLAIN_MESSAGE); 
     dialog.dispose(); 

     // Open a Bufferreader to read in questions from the Test file. 
     try (BufferedReader fileReader = new BufferedReader(new FileReader(testFilePath))) { 
      // Iterate through the Test file and process one question at a time.... 
      String testFileLine = ""; 
      while ((testFileLine = fileReader.readLine()) != null) { 
       // Split the file line question into specific parts. 
       // 1st part will be the question itself, 2nd part will be 
       // the answer and the 3rd part will be the number of seconds 
       // allowed to answer question. If the 3rd part is not supplied 
       // within the file line question then a default of 10 seconds 
       // is used as set by the defaultSecondsForTimout class global 
       // variable. 
       String[] fileQuestionParts = testFileLine.split("\\|"); 
       String question = fileQuestionParts[0]; 
       // Allow for newline and tab tags within text string. 
       question = "\n" + question.replaceAll("\\\\n", "\n").replaceAll("\\\\t", "\t"); 
       //Get the question answer from file line 
       String questionAnswer = fileQuestionParts[1]; 
       // If the seconds time out is provided within the question file 
       // line then grab it for use. If 0 is supplied then there is no 
       // time limit on that particular question. 
       if (fileQuestionParts.length > 2) { secondsForTimout = Integer.parseInt(fileQuestionParts[2]); } 
       // otherwise use the default of 10 seconds. 
       else { secondsForTimout = defaultSecondsForTimout; } 


       String answerResult = ""; 
       questionCount++; // Increment the questionCount variable 
       questionAnswered = false; // Set the qustionAnswered variable 

       // Ask the retrived question to User.... 
       answerResult = askTimedQuestion(question, secondsForTimout); 
       questionAnswered = true; 

       // If the User entered quit then quit the test. 
       if (answerResult.equalsIgnoreCase("quit")) { break; } 

       // If the User supplied input is the right answer then... 
       if (answerResult.equalsIgnoreCase(questionAnswer)) { 
        System.out.print(blueColor + " CORRECT\n " + resetColor); 
        rightAnswers++;  // Increment the rightAnswers variable. 
       } 
       // If the User supplied input is the wrong answer then...   
       else { 
        wrongAnswers++;  // Increment the wrongAnswers variable. 
        System.out.print(redColor + " WRONG\n " + resetColor); } 
      } 
      // Close the file reader. 
      fileReader.close(); 
    } 
     catch (IOException e) { 
      // Display file errors 
      System.out.println("\nERROR! - " + redColor + e.getMessage() + resetColor); 
     } 
    } 

    // Method for asking the questions retrieved from the supplied Test file 
    private static String askTimedQuestion(String question, int secondsPerQuestion) { 
     // The secondsPerQuestion parameter allows you to change 
     // the number of seconds for each question if seconds are 
     // applied to a particular question within the Test file. 
     secondsForTimout = secondsPerQuestion; 

     // Establish a new Thread for perform our question timing... 
     Thread timerThread = new Thread(new Runnable() { 
      @Override 
      public void run() { 
       try { 
        // See if this thread has been interrupted. If it has then 
        // we stop our timer While/Loop (a gracefull Thread Stop). 
        while (!Thread.currentThread().isInterrupted()) { 
         for (int seconds = secondsForTimout; seconds >= 1; seconds--){ 
          // Break out of this timer FOR loop if the question 
          // was answered by using Thread.interrupt(). 
          if (questionAnswered) { Thread.currentThread().interrupt(); break;} 
          // Show that timer is ticking away... 
          System.out.print(purpleColor + "*" + resetColor); 

          // ========================================================== 
          // Or you can use this... 
          //if (seconds < secondsForTimout) { System.out.print("-"); } 
          //System.out.print(seconds); 
          // ========================================================== 
          Thread.sleep(1000); 
         } 

         // If the question wasn't answered and our timer loop has 
         // expired then inform User that time is up and set the 
         // timeOut variable to true. 
         if (!questionAnswered) { 
          System.out.print("\b\b\b\u001B[31mYour time is up for this question!\u001B[39;49m"); 
          timeOut = true; 
         } 
        } 
       } catch (InterruptedException e) { 
        Thread.currentThread().interrupt(); 
       } 
      } 
     }); 

     // Catch Exceptions for BufferReader()/InputStreamReader()... 
     try { 
      // Declare a BufferReader object so as to get input from User. 
      // We use BufferReader along with InputStreamReader(System.in) 
      // for this. 
      BufferedReader br = new BufferedReader(new InputStreamReader(System.in)); 

      // Display the supplied Question from file to User... 
      if (questionCount > 1) { 
       System.out.println("\n------------------------------------------------------"); 
      } 
      System.out.print(blueColor + "[" + secondsForTimout + " seconds]" + resetColor); 
      System.out.println(question); 

      // Declare User input variable & initialize to a Null String 
      String input = "";  

      // Reset the timeOut variable 
      timeOut = false;  

      // Make sure our timer thread is dead before restarting it. 
      //while (timerThread.isAlive()){} 
      // Start the Timer Thread 
      if (secondsPerQuestion > 0) { timerThread.start(); } 

      // Loop through input from the User 
      do { 
       // Wait until we have User input data to complete a readLine() 
       // or until our timer thread has set the timeOut variable to 
       // true. 
       while (!br.ready()) { 
        // If our timer thread has set the timeOut variable to 
        // true then let's get outta this question altogether. 
        // First we get out of our 'wait for input' loop... 
        if (secondsPerQuestion > 0 && timeOut) { break; } 
       } 
       // Then we get out of our Do/While Loop. 
       if (secondsPerQuestion > 0 && timeOut) { break; } 

       // No time-out so let's move on... 
       // Let's see what the User supplied for an answer. 
       // If just ENTER was supplied then input will contain 
       // a Null String and the User can still enter an answer 
       // until the question is timed out. 
       input = br.readLine(); 

       // remove any unwanted text from System.out.print() 
       // that had made its way through the timer thread. 
       System.out.print("\b\b\b\b\b"); 

      } while ("".equals(input)); 

      // Stop the timer thread. 
      timerThread.interrupt(); 

      return input; 
     } 
     catch (IOException ex) { return ""; } 
    } 

    // Determine & return the Letter Grade for the 
    // supplied integer test percentage score. This 
    // is a typical North American Standard (I think?). 
    private static String getLetterGrade(int score) { 
     String grade = ""; 
     if (score >= 90) { grade = "A"; } 
     if (score >= 80 && score <= 89) { grade = "B"; } 
     if (score >= 70 && score <= 79) { grade = "C"; } 
     if (score >= 60 && score <= 69) { grade = "D"; } 
     if (score >= 0 && score <= 59) { grade = "F"; } 
     return grade; 
    } 
} 

私が言ったように...ただ別の方法です。