This question already has answers here:
Non repeating random numbers
(2 answers)
Closed 8 years ago.
I've made a random wrestling match generator that I've adapted from a random phrase generator from a textbook. I'd like to know how to make it so the same name isn't done twice on the same run. Can't have The Crusher vs. The Crusher, right?
public class matchOMatic {
public static void main (String [] args) {
String [] wordListOne = {"The Crusher", "The Main Man", "The Macho-man, Randy Savage", "The Nature Boy, Rick Flare", "Batista", "Hollywood Hulk Hogan", "Vader", "The Undertaker", "Stone Cold Steve Austin" };
String [] wordListThree = {"The Crusher", "The Main Man", "The Macho-man, Randy Savage", "The Nature Boy, Rick Flare", "Batista", "Hollywood Hulk Hogan", "Vader", "The Undertaker", "Stone Cold Steve Austin"};
int oneLength = wordListOne.length;
int threeLength = wordListThree.length;
int rand1 = (int) (Math.random() * oneLength);
int rand3 = (int) (Math.random() * threeLength);
String phrase = wordListOne[rand1] + " and in the opposite corner is his opponent, " + wordListThree[rand3];
System.out.print("In this corner we have " + phrase);
System.out.println("!");
}
}
Very simple solution for this!
Just put this after you give values to rand3 and rand2:
while(rand3 == rand1) {
rand3 = (int) (Math.random() * threeLength);
}
This will keep choosing a new value for rand3 until the values are different!
I hope this helps. Good luck with your program :)
The cleanest solution is to store the names in an ArrayList rather than an array of strings, shuffle the list, and iterate through in pairs to create matches. Shuffling a list of length N is O(N), and this is guaranteed to not produce duplicates across the scheduled matches.
You could pick the next one ( or the one before) if the random turns out to be the same.
if ( rand3 == rand1 )
rand3 = (rand3 +1) % threeLength
Edit:
As noted below this creates bias which is not good.
other possible solution is not to include the first randomly picked index in the next random roll
// -1 because we are not including the same pick
int rand3 = (int) (Math.random() * ( threeLength-1) );
// fix the index because we haven't actually removed it from the array
if (rand3 >= rand1)
rand3 = (rand3 +1) % threeLength
Related
how many dice dots do u want?
6
try 1 : 2
try 2 : 4
try 3 : 5
try 4 : 6
In 4 try's u found 6 dots
So this is what I'm trying to get as output, but can't seem to find how.
System.out.println("how many dice dots do u want?");
int dots = s.nextInt();
int dots2 = (int) (6 * Math.random()) + 1;
This is what I have. I tried a for loop now, but it doesn't seem to work. Can someone help me?
You can achieve what you want this way:
Scanner scan = new Scanner (System.in);
int randomValue = 0; //this is the random value that'd be autogenerated in each loop
int counter = 1; //this represents the number of trials
System.out.println("how many dice dots do u want?");
int dotsWanted = scan.nextInt();
while(randomValue != dotsWanted){
randomValue = (int) (6 * Math.random()) + 1;
counter++;
}
System.out.printf("In %d trials, %d dots were found\n", counter, dotsWanted);
I hope this helps.. Merry coding!
Please, format your question properly next time, it helps us to help you :)
You need a while loop to throw the dice.
int dots = s.nextInt();
boolean found = false;
Random rnd = new Random();
while(!found) {
int rolled= rnd.nextInt(6) + 1;
if(rolled == dots) // do your stuff
found = true;
}
Hope it helps.
I have a small problem when trying to generate a random string with random size (between 3 and 20). I have an array arr with all characters from a (lowercase) to Z (uppercase). I then generate a random length arrLength for a second array arr2, which will be containing some randomly selected chars.
My issue is that the letter 'a' (lowercase) never appears in my randomly generated strings. I think that the mistake might be inside the for loop, but I have failed to see it so far. Maybe it has something to do with (int) casting or Math.floor rounding?
char[] arr = "abcdefghijklmnopqrstuwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ".toCharArray();
int arrLength = (int) (Math.floor((Math.random() * ((17 - 3) + 1)) + 3));
char[] arr2 = new char[arrLength];
String str = "";
for(int i=0;i<arrLength;i++) {
char num = arr[(int) (Math.floor(Math.random() * (50) + 1))];
arr2[i] = num;
}
Instead of the magic constant 50 use arr.length (note there are more than 50 characters in the array) and leave out the +1 as it makes the lowest number you can get to 1 and array indices start at 0 in Java.
I want a random number, either 0 or 1 and then that will be returned to main() as in my code below.
import java.util.Scanner;
public class Exercise8Lab7 {
public static void main(String[] args) {
Scanner input = new Scanner(System.in);
int numFlips = 0;
int heads = 0;
int tails = 0;
String answer;
System.out.print("Please Enter The Number Of Coin Tosses You Want: ");
numFlips = input.nextInt();
for(int x = 1;x <= numFlips; x++){
if(coinToss() == 1){
answer = "Tails";
tails++;
}
else{
answer = "Heads";
heads++;
}
System.out.print("\nCoin Toss " + x + ": " + answer);
}
System.out.println("\n\n====== Overall Results ======" +
"\nPercentage Of Heads: " + (heads/numFlips)*100 + "\nPercentage Of Tails: " + (tails/numFlips)*100);
}
public static int coinToss(){
double rAsFloat = 1 * (2 + Math.random( ) );
int r = (int)rAsFloat;
return r;
}
}
Many solutions had been suggested to use the util.Random option which I have done and works perfectly but I want to sort out why I can't get this to work. Obviously I want the number to be an int myself so I convert it to an int after the random number has been generated. But no matter what I add or multiply the Math.random() by, it will always all either be Heads or all either be Tails. Never mixed.
Try this) It will generate number 0 or 1
Math.round( Math.random() ) ;
You could use boolean values of 0 or 1 based on value of Math.random() as a double between 0.0 and 1.0 and make the random generator much simpler. And you can get rid completely of the coinToss() method.
if(Math.random() < 0.5) {
answer = "Tails";
tails++;
}
Remove the coin toss method and replace the first conditional with the code above.
Math.random(); by itself will return a value between 0.0 and less than 1.0. If the value is in the lower half, [0.0, 0.5), then it has the same probability of being in the upper half, [0.5, 1.0). Therefore you can set any value in the lower half as true and upper as false.
Wierd that no one is using a modulo division for the random number.
This is the simplest implementation you can get:
Random rand = new Random();
int randomValue = rand.nextInt() % 2;
Math.round(Math.random()) will return either 0.0 and 1.0. Since both these values are well within the limits of int range they can be casted to int.
public static int coinToss(){
return (int)Math.round(Math.random());
}
(int)(Math.random()*2) also works fine in this case
its not working because of the integer math you are using, the call to 2+ Math.Random is pretty much always giving you a answer between 0.0 and 1.0.
so assuming that you recieve 0.25 as your result your maths is as follows
double d = 1* (2 + 0.25); // (result = 2
Then you are checking to see if your result == 1 ( which it never will. )
A better result would be to declare java.util.Random as a class variable and call random.nextBoolean() and simply perform your heads/tails calculation on that.
If you were to continue to use Math.random() and lets say
return Math.random() < 0.5
Your results would be ever so slightly skewed due to the fact that Math.random() cannot return 1.0, due to the fact that the java API specification states:
"Returns a double value with a positive sign, greater than or equal to 0.0 and less than 1.0."
Math.random() returns a random float in the range [0.0,1.0)--that means the result can be anything from 0 up to but not including 1.0.
Your code
double rAsFloat = 1 * (2 + Math.random( ) );
will take this number in the [0.0,1.0) range; adding 2 to it gives you a number in the [2.0,3.0) range; multiplying it by 1 does nothing useful; then, when you truncate it to an integer, the result is always 2.
To get integers from this kind of random function, you need to figure out how many different integers you could return, then multiply your random number by that. If you want a "0 or 1" answer, your range is 2 different integers, so multiply Math.random() by 2:
double rAsFloat = 2 * Math.random();
This gives you a random number in the range [0.0,2.0), which can then be 0 or 1 when you truncate to an integer with (int). If, instead, you wanted something that returns 1 or 2, for example, you'd just add 1 to it:
double rAsFloat = 1 + 2 * Math.random();
I think you've already figured out that the Random class gives you what you want a lot more easily. I've decided to explain all this anyway, because someday you might work on a legacy system in some old language where you really do need to work with a [0.0,1.0) random value. (OK, maybe that's not too likely any more, but who knows.)
The problem can be translated to boolean generation as follow :
public static byte get0Or1 {
Random random = new Random();
boolean res= random.nextBoolean();
if(res)return 1;
else return 0;
}
Here it the easiest way I found without using java.util.Random.
Blockquote
Scanner input = new Scanner (System.in);
System.out.println("Please enter 0 for heads or 1 for tails");
int integer = input.nextInt();
input.close();
int random = (int) (Math.random() + 0.5);
if (random == integer) {
System.out.println("correct");
}
else {
System.out.println("incorrect");
}
System.out.println(random);
This will take a random double from (0 to .99) and add .5 to make it (.5 to 1.49). It will also cast it to an int, which will make it (0 to 1). The last line is for testing.
for(int i=0;i<100;i++){
System.out.println(((int)(i*Math.random())%2));
}
use mod it will help you!
One more variant
rand.nextInt(2);
As it described in docs it will return random int value between 0 (inclusive) and the specified value (exclusive)
I have to make a Poker Dice game for class. I am able to successfully random five numbers 1 to 6 (to resemble rolling a die five times). However, I need to show "Nine" for 1, "Ten" for two, etc. I am using an array to hold the numbers. I can't seem to figure out how to assign a string output for each int.
public static void main(String[] args) {
int[] player = new int[5];
String[] cards = new String[] {"Nine", "Ten", "Jack", "Queen", "King", "Ace"};
System.out.println("User: " + playerHand(player, cards));
}
public static String playerHand(int[] player, String[] cards) {
String hand = "";
for (int i = 0; i < player.length; i++) {
player[i] = (int) (Math.random() * (6 - 1) + 1);
hand += player[i] + " ";
}
return hand;
}
You've put your strings in an array, so you just add an element from the array to your hand string:
hand += cards[player[i]] + " ";
There is, however, still a problem with your code. You obtain the random numbers as follows:
player[i] = (int) (Math.random() * (6 - 1) + 1);
You probably expect this to be a number from 1 to 6. However, Math.random() returns a double from 0 (inclusive) to 1 (exclusive). That means that player[i] will never be assigned 6. This error kind of solves another error: since Java arrays are zero-based, the element with index 6 does not exist. (Thus, if 6 would have been chosen, your program would have aborted with an error message.) But still, the number 0 and thus the word "Nine" will never appear in your solution. So you have to change the two lines to:
hand += cards[player[i] - 1] + " ";
and
player[i] = (int) (Math.random() * 6 + 1);
respectively.
Consider making the cards array a static class member; then you don't need to pass the array to the playerHand method as an argument.
You might use a switch block
switch(array[i]){
case 1:
printf("One\n");
break;
case 2:
printf("Two\n");
break;
etc...
I'm trying to create a blackjack game, where the player starts off with 2 cards, and then asked if he/she would like to have another card (user input: yes or no), if yes, another card is added to the total. if no, the game just terminates.
Here is a sample output I'm trying to get:
And this is what I have so far (It's probably wrong in terms of the placement):
import java.util.Scanner;
public class BlackJackGame {
public static void main(String[] args) {
int randomnum1 = (int) (1 + Math.random() * 10);
int randomnum2 = (int) (1 + Math.random() * 10);
int randomnum3 = (int) (1 + Math.random() * 10);
int total;
char anotherCard = 'y';
Scanner input = new Scanner(System.in);
System.out.println("First cards: " + randomnum1 + ", " + randomnum2);
total = randomnum1 + randomnum2;
System.out.println("Total: " + total);
while (anotherCard != 'n')
{
System.out.print("Card: " + randomnum3);
System.out.print("Do you want another card? (y/n): ");
anotherCard = input.next().charAt(0);
}
}
}
Tips and reworking the source code will be highly appreciated.
As Far as card games go, there are 52 cards in a deck, and I'm assuming there's one deck.
If you want it to be a fair game, then you have to keep that in mind.
But if you just want output to look correct, you just have to avoid getting more than 4 aces, 2's, 3's, and 4's.
One way to achieve this would be to make an int array of size 52 with 4 of each card. I suppose Ace would be 1 and 10,J,Q,K would be 10, so there would be 16 10's.
Get a random number between 0 and 51 to get the index of the array you want to use. Once you use that index, set the value of that array = -1, and always check for -1 before using that index, and if it is -1, get another random value.
int [] deck = size 52 array with 4 of each card.
int random = get random number between 0 and 51.
while(deck[random] == -1){
random = get random number between 0 and 51.
}
int card1 = deck[random]
deck[random] = -1;
something like that.. I just did that quickly, hopefully you get the idea.
Here are the tips you requested:
You need to introduce a variable to keep track of your sum. For example, you could initialize it with: int sum = randomnum1 + randomnum2; and keep adding the next card to it inside the loop: sum += randomnum3;
You need to generate randomnum3 inside the while loop. This way, you will get a different card every time. Basically, you have to call the random function every time you generate a card, not just once. Otherwise the value of randomnum3 will be unchanged and you will get the same card over and over.
To exit when you get to 21, you would have to use if and possibly break within the loop, once you have added the current card to the sum: if(sum > 21) { break; }
Alternatively, you can set the value of anotherCard to 'n' instead of using a break
You should keep track of which cards the user has already gotten if you want to simulate an actual deck. This is not technically necessary for the program you appear to be writing though.
Here are a few simple improvements for you to look over. I'll leave it like this as part of the joy of learning to program is in the discovery. As a next step I'd suggest generating a dealers hand and then seeing if the player can beat it. Good luck!
public static void main(String[] args) {
int card1 = (int) (1 + Math.random() * 10);
int card2 = (int) (1 + Math.random() * 10);
int total = card1 + card2;
System.out.println(String.format("First cards: %d & %d. Total %d", card1, card2, total));
System.out.println();
Scanner input = new Scanner(System.in);
System.out.print("Do you want another card? (y/n): ");
char anotherCard = input.next().charAt(0);
while (anotherCard != 'n' && total < 21) {
int nextcard = (int) (1 + Math.random() * 10);
total += nextcard;
System.out.println(String.format("You drew a %d. Your total is now %d", nextcard, total));
if (total > 21) {
System.out.println("You busted!");
} else {
System.out.print("Do you want another card? (y/n): ");
anotherCard = input.next().charAt(0);
}
}
}