Reputation: 9
I'm using Java for this problem. Does anyone know how to randomly take 2 questions out of 3 question String array? Lets say I have a 3x5 string array like this:
String TestBank[][] = {{"What color is grass?","A. Green","B. Red","C. Pink","A"},
{"Whats the first month called?","A. December","B. January","C. March","B"},
{"What shape is a soccer ball?","A. square","B. flat","C. round","C"}};
The first column is the question, 2nd-4th column is the answer choices, and the 5th column is the correct answer. I'm trying to figure out how to randomly get 2 questions from these 3 and store those 2 questions into a one dimensional array of 2 rows in which we use the JOptionPane, for outputting, in which takes those questions from the one dimensional array and shows each question separately one by one in different windows with the answer choices included. And after answering the 2 questions, it tells the user the score based off how many questions he/she missed.
I'm relatively new to Java and it would be greatly appreciated if someone could help me with this.
Upvotes: 1
Views: 1216
Reputation: 152
Here is an answer that handles the possibility that the random generator generates the same question twice. With the code below you will only ever get 1 question asked. Also I have commented each step to give you an idea of the logic. One small point if you had a 1D array of type int, then you would run into problem during the check. This is because 1D arrays of type int set the default value to 0. Using Integer or an ArrayList eliminates this problem because default value is null and not 0.
I have also included the loop and JOptionPane code required to display the randomly chosen question. It is up to you to decide what you want to do with the responses.
public static void main(String args[]) {
// We are setting this final variable because we don't want to hard code numbers into loops etc
final int NUMBER_OF_QUESTIONS_TO_TAKE = 2;
String testBank[][] = {{"What color is grass?", "A. Green", "B. Red", "C. Pink", "A"},
{"Whats the first month called?", "A. December", "B. January", "C. March", "B"},
{"What shape is a soccer ball?", "A. square", "B. flat", "C. round", "C"}};
// Initialise the array of questions that have been randomly chosen.
String finalArrayOfQuestions[] = new String[NUMBER_OF_QUESTIONS_TO_TAKE];
// ArrayList to store the index number of a question so we can check later if it has been already used by number generator
ArrayList<Integer> alreadyChosenList = new ArrayList<Integer>();
// boolean that we will use for whether or not a question has already been selected
boolean alreadyChosen;
// The column number that the random number generator generates, which is then used to extract the String question
int rowToUse;
// A for loop is used to loop through the process, depending on how many questions you want to take.
for (int i = 0; i < NUMBER_OF_QUESTIONS_TO_TAKE; i++) {
// Generate a random number, repeat the process (do/while) until a random number has been generated that hasnt been generated before
do {
// Generate a random number within the range
Random random = new Random();
rowToUse = random.nextInt(testBank.length);
//check not already been picked
alreadyChosen = alreadyChosen(rowToUse, alreadyChosenList);
} while (alreadyChosen);
// Get String representation of question chosen at random
String questionChosen = testBank[rowToUse][0];
// Add this String to finalListOfQuestions
finalArrayOfQuestions[i] = questionChosen;
// adds to list of questions already chosen. Makes sure you don't take same question twice.
//alreadyChosenList[i] = alreadyChosenList[rowToUse];
alreadyChosenList.add(rowToUse);
}
for (String questions : finalArrayOfQuestions) {
String response = JOptionPane.showInputDialog(questions);
/*
The response is the answer that the user types in. Here you can check it against the arrays you have
Or if you dont want the user to input a response use:
JOptionPane.showMessageDialog(null, questions);
*/
}
}
/*
Method takes row index to use and the ArrayList of row indexes already been used and returns true or false depending if the current one is in the arraylist
*/
private static boolean alreadyChosen(int rowToUse, ArrayList<Integer> alreadyChosenList) {
for (int indexToCheck : alreadyChosenList) {
if (indexToCheck == rowToUse) {
return true;
}
}
return false;
}
Upvotes: 0
Reputation: 93948
Shuffling and then shortening the array is probably the way to go. This is more easily done on lists however. In general collection classes should be preferred over arrays.
Most of the work in this answer is performed to convert the arrays to a list and back again.
private static String[][] randomize(String[][] testBank, int questions) {
// convert top array to list of mutable size
List<String[]> testBankAsList = new ArrayList<>();
for (String[] qoa: testBank) {
testBankAsList.add(qoa);
}
// randomize questions
Collections.shuffle(testBankAsList, new SecureRandom());
// remove the tail
testBankAsList.subList(questions, testBankAsList.size()).clear();
// convert back into array
String[][] shorterRandomTestBank = testBankAsList.toArray(new String[testBankAsList.size()][]);
return shorterRandomTestBank;
}
Where questions
should be set to 2 of course. I left out all the parameter checking.
Note that Arrays.toList
cannot be used as it simply creates a list over the backing array, and therefore the clear()
operation will fail.
Example usage:
public static void main(String[] args) {
String testBank[][] = {{"What color is grass?","A. Green","B. Red","C. Pink","A"},
{"Whats the first month called?","A. December","B. January","C. March","B"},
{"What shape is a soccer ball?","A. square","B. flat","C. round","C"}};
int questions = 2;
String[][] shorterRandomTestBank = randomize(testBank, questions);
// iterate of the returned questions
for (String[] qoa : shorterRandomTestBank) {
// prints the question
System.out.println(qoa[0]);
// prints the answer
System.out.println(qoa[qoa.length - 1]);
}
}
Sorry, I'll let you do the Swing / GUI programming yourself. If you get into trouble with that ask a separate question.
Upvotes: 0
Reputation: 4076
This is how you use random class in your case. Choose a random integer, where the highest number chosen by random is your total number of questions.
Random random = new Random();
int randomQuestion = random.nextInt(nrOfQuestions);
and you use this randomQuestion variable to access you question from the matrix: testBank[randomQuestion][0]
Cheers!
Upvotes: 1