How to program a dice race - java

I'm taking a programming II class in which we've been working on programming classes. Now we've been assigned homework to write a driver class to incorporate these classes. The homework states
Using the die, dice, and player classes completed in class, write a
driver class to have three players taking turns rolling the dice.
First player to accumulate a total score of 35 or more is the winner."
For example, if player 1 rolls a 3, their score is 3. Then player 2
rolls. Then player 3. As each player rolls, their roll is added to
their previous score.
I've started writing it, but have been given the error that several items in my program cannot be resolved to a type. I also have absolutely no idea how to even begin creating a loop to do what is being asked. This is what I have so far:
import java.util.Scanner;
public class DiceRace {
public static void main(String[] args){
Player player1;
Player player2;
Player player3;
Dice dice;
Scanner keyboard;
keyboard=new Scanner(System.in);
dice=new Dice();
System.out.print("First player's name: ");
player1=keyboard.next();
System.out.print("Second player's name: ");
player2=keyboard.next();
System.out.print("Third player's name: ");
player3=keyboard.next();
}//Ending bracket of method main
}//Ending bracket of class DiceRace

You can create 3 methods, for each player, and a method that plays the game. In each player's method, it first calls the play method with a parameter containing the player name, and the play method prints it out so that the player knows who's turn it is. once the play method is done, it will call the next player method, then the player after that, and finally back to player 1.

It looks like you're a beginner. You should do some tutorials or stuff like that to know the basics :) Also, if you start getting familiar with an IDE (like Eclipse) then programming will be far more easy for you as IDEs can give you detailed descriptions of errors, even while writing the code.
In your above example you need to create two classes by yourself Dice and Player, as they are not in Java by default.
The method keyboard.next() reads an input from the console and returns it as object of the type String, not Player. Thus, you can not assign the variable player1 the result, a String.
What you probably want is a Player object having a member variable String name. Here's an example:
public final class Player {
private String mName;
public Player(final String name) {
mName = name;
}
public String getName() {
return mName;
}
}
Then you can do something like this in your main-method:
player1 = new Player(keyboard.next());
System.out.println("Name of player1 is: " + player1.getName());
Next you probably want a Dice to have a roll method:
public final class Dice() {
private Random mRandom;
public Dice() {
mRandom = new Random();
}
public int roll() {
// Returns a random number between 1 and 6 (inclusive)
return mRandom.nextInt(6) + 1;
}
}
Then, in your main you can do:
Dice dice = new Dice();
System.out.println("Let's roll the dice: " dice.roll());
Now to the games logic, let's keep it very simple, beginner friendly:
int player1Score = 0;
int player2Score = 0;
int player3Score = 0;
boolean finished = false;
boolean player1One = false;
boolean player2One = false;
boolean player3One = false;
// 0 is first player, 1 second and 2 third
int currentPlayer = 0;
while(!finished) {
int rollValue = dice.roll();
if (currentPlayer == 0) {
player1Score += rollValue;
} else if (currentPlayer == 1) {
player2Score += rollValue;
} else {
player3Score += rollValue;
}
player1One = player1Score >= 35;
player2One = player2Score >= 35;
player3One = player3Score >= 35;
finished = player1One || player2One || player3One;
// Increment and modulo 3 (numbers between 0 and 2)
currentPlayer = ((currentPlayer + 1) % 3);
}
Good luck :)

Related

Troubled with how and where to implement if/else statements

I am almost finished creating a hangman game in Java, although I am having difficulty with one last part. I want to make it so the program checks if all the letters of the word have been guessed correctly and if so, the game prints a message saying they have won, the game ends and the program goes to the do while loop in the main class asking if they would like to play again. If not however, the game continues until this point or if all 5 guesses have been used - to which again, it is sent to the do while loop in order to restart the game and not simply terminate the program.
The problem is I am unsure how and where exactly to structure the if and else statements in order to do so.
Any help would be greatly appreciated, if I can provide further information to help narrow anything down please ask too, thank you in advance.
Instantiable Class
public class Hangman {
private char letterGuess;
private int numberLives;
private String outputWord, endMessage;
private final String hiddenWord;
private final StringBuffer swapBuffer = new StringBuffer();
public Hangman() {
letterGuess = ' ';
numberLives = 5;
hiddenWord = "java";
outputWord = "";
endMessage = "";
for (int i = 0; i < hiddenWord.length(); i++) {
swapBuffer.append("*");
}
}
public void setLetterGuess(char letterGuess) {
this.letterGuess = letterGuess;
}
public void compute() {
boolean letterFound = false;
for (int i = 0; i < hiddenWord.length(); i++) {
if (letterGuess == hiddenWord.charAt(i)) {
swapBuffer.setCharAt(i, letterGuess);
letterFound = true;
}
}
if (!letterFound) numberLives--;
outputWord = swapBuffer.toString();
}
public int getNumberLives() {
return numberLives;
}
public String getHiddenWord() {
return hiddenWord;
}
public String getOutputWord() {
return outputWord;
}
public String getEndMessage() {
return endMessage;
}
}
Main Class
import javax.swing.*;
public class HangmanApp {
public static void main(String[] args) {
char letterGuess;
int numberLives;
String hiddenWord, outputWord, endMessage, restartGame;
do {
Hangman myHangman = new Hangman();
JOptionPane.showMessageDialog(null, "Welcome to Java Hangman!");
JOptionPane.showMessageDialog(null, "In this game, a word will be printed to you in asterisks - each letter will be revealed upon a correct guess!");
JOptionPane.showMessageDialog(null, "You have 5 lives for the game, the game will end if you make too many incorrect guesses!");
for (int i = 0; i < 10; i++) {
hiddenWord = myHangman.getHiddenWord();
numberLives = myHangman.getNumberLives();
JOptionPane.showMessageDialog(null, "You currently have " +numberLives+ " lives!");
letterGuess = JOptionPane.showInputDialog(null, "Now, please enter a letter : ").charAt(0);
myHangman.setLetterGuess(letterGuess);
myHangman.compute();
outputWord = myHangman.getOutputWord();
JOptionPane.showMessageDialog(null, "The word so far is : " +outputWord);
}
numberLives = myHangman.getNumberLives();
JOptionPane.showMessageDialog(null, "You have finished the game with : " +numberLives+ " lives!");
restartGame = JOptionPane.showInputDialog(null, "Would you like to play again?");
}
while (restartGame.equalsIgnoreCase("Yes"));
}
}
Here's the way I see it. After you call myHangman.compute();, you want to check to see if the player has either won the game or run out of lives. Each of these is a separate test using an if expression. There is no else part because if the test fails, the game just goes on.
If one of these conditions is recognized, then you want to display a message, and then you want to exit the current game loop so the user will be asked if they want to play another game. The way to do this is with the break statement.
One issue you have is that you don't have a way in your main game loop to ask the Hangman class if the user has guessed the whole word. To be able to do this, you can add this method to the bottom of your Hangman class:
public boolean getAllLettersFound() {
return outputWord.indexOf('*') < 0;
}
This method checks to see if there are any * in outputWord. If not, then the user has guessed all the letters. So with this method added, the main loop can query the Hangman object to find out if the player has won.
To put this all together, you need to add the two condition checks to your main game loop, right after you call myHangman.compute();. Here are those two if blocks:
if (myHangman.getAllLettersFound()) {
JOptionPane.showMessageDialog(null, "You Won!!!!");
break;
}
if (myHangman.getNumberLives() == 0) {
JOptionPane.showMessageDialog(null, "You Ran Out Of Guesses");
break;
}
That should do it. Happy coding!

Why does my Java dice game keep repeating its roll?

I have made a Dice game in Java using two files. The code runs perfectly, but it seems to have a logical error in it that I don't understand. In the game, it only outputs the same value as the previous roll. So if the die rolled a 6 and you rolled again, it would say you rolled a 6 again continuously. I'm trying to fix it currently but am having trouble. Any help would be greatly appreciated.
Here are the two programs:
import java.util.Scanner;
public class DiceGameTest {
static Scanner input = new Scanner(System.in);
public static void main(String[] args) {
//declare instance variables
int choice = 0;
//int total;
//total = die1.getRoll() + die2.getRoll();
//create the 2 die
Dice die1 = new Dice();
//Dice die2 = new Dice();
//print out description of game
System.out.println("Welcome to Eric and John's Dice game!");
System.out.println("This dice game is very simple, here are the rules!");
System.out.println(" 1. Roll a die");
System.out.println(" 2. To win, you must get a 4 or higher");
System.out.println(" 3. Have Fun!\n");
//ask the user if they want to roll the dice or quit
System.out.println("Would you like to roll the die to start playing? Press 1 to roll or \"-1\" to quit");
//user's choice
choice = input.nextInt();
//if the user puts 1
if(choice == 1)
{
System.out.printf("You rolled a %d%n", die1.getRoll());
}
//play the game
do
{
die1.getRoll();
if(die1.getRoll() >= 4)
{
System.out.println("Hooray! You won by getting a: " + die1.getRoll());
}
else if(die1.getRoll() < 4)
{
System.out.println("Too Bad! Your roll was: " + die1.getRoll() + " and it was not greater than or equal to 4");
}
//ask the user if they want to roll the dice again or quit
System.out.println("Would you like to roll the die to start playing? Press 1 to roll or \"-1\" to quit");
//user's choice
choice = input.nextInt();
}while(choice != -1);
if(choice == -1)
{
System.out.println("You Quit the Game!");
}
}
}
And this
import java.util.Random; //class used to generate random number for dice roll
public class Dice {
private int numberSides;
private Random randomGenerator;
private int currentRoll;
//default constructor
Dice() {
randomGenerator = new Random(); //initialize random object
numberSides = 6; //default number of sides
currentRoll = randomGenerator.nextInt(numberSides)+1; //initialize roll (1-6)
}
public int getRoll() {
return currentRoll;
}
//"roll" a random integer between 1 and numberSides
public void roll() {
currentRoll = randomGenerator.nextInt(numberSides)+1; //reroll 1-6
}
}
Right now you just keep calling die1.getRoll at the beginning of your loop. That number is not changing unless you call roll.
Remove currentRoll from your constructor. You don't need to put it there. Then,
die1.getRoll()
Should be,
die1.roll()
In your do while loop like this
do
{
die1.roll();
if(die1.getRoll() >= 4)
{
System.out.println("Hooray! You won by getting a: " + die1.getRoll());
}
else if(die1.getRoll() < 4)
//rest of it
Alternatively, you could make a few modifications in your game and change your function.
public int getRoll()
{
roll();
return currentRoll;
}
Why does my Java dice game keep repeating its roll?
You keep getting the same random number because the only code which is responsible for generating a new random number lies in the constructor of your Dice class.
The constructor will only be invoked once upon instantiation. Calling getRoll() subsequently will just return you the same random number.
If you want to receive a new random number from getRoll(), you can do it as:
public int getRoll(){ //return a new dice roll every time
return (randomGenerator.nextInt(numberSides)+1);
}
If you like the Dice class to "remember" the current roll, you can have a method like:
public int roll(){ //return a new dice roll every time & save current
currentRoll = randomGenerator.nextInt(numberSides)+1;
return currentRoll;
}
How would I go about calling the roll()function a getRoll() function? Could you please specify?
You don't need both roll() and getRoll(), either one is enough to generate a new random number. You just have to make sure you are placing randomGenerator.nextInt(numberSides)+1 in your roll() or getRoll() method to make it work.

Replace 'menu' with input from user

In the interest of learning I decided to write up a coin flipping program. The coin is an enum and i have the program return that enum value. I also have the user input from a menu style but this was helped by following along in a Barnes and Nobles book I purchased a while back.
I think I have come to a weird cross road. i was wanting to basically return the enum value and such but remove the 'menu' aspect and replace it with the ability for the user to input how many flips they would like to do and also repeat the program if they want to (so instead of pressing 1 to flip each time they can input say 20000 and it would flip that many times i also think doing this would help with a fairness check as a true test of fairness would return almost even amounts of heads and tails if it were to flip that many times then pressing 0 for no flips would end the program) and i want to prompt the user and ask if they would like to repeat.
here is the program I have written:
import java.util.*;
public class CoinTossing
{
private enum Coin { HEADS, TAILS };
private static final Random randomNumbers = new Random();
private static final int HEAD = 1;
private static final int TAIL = 2;
public static void main(String[] args)
{
Scanner input = new Scanner( System.in );
int choice;
int toss = 0;
int tosses = 0;
int frontflip = 0;
int backflip = 0;
Coin gameStatus;
System.out.println("Welcome to the Coin Toss Program.\n");
System.out.println("Choose from the menu what you want to do.");
System.out.print("1. Toss the coin\n2. Quit program\n");
choice = input.nextInt();
while ( choice != 0 )
{
if ( choice == 1 )
{
int CoinTossed = Flip();
switch ( CoinTossed )
{
//added tosses to switch statement to make the counter work perfect.
case HEAD:
gameStatus = Coin.HEADS;
tosses++; // add amount of tosses
break;
default: // changed case TAIL to default. Easy and works.
gameStatus = Coin.TAILS;
tosses++; // add amount of tosses
break;
}
if ( gameStatus == Coin.HEADS )
{
frontflip++; //Add amount of heads
}
else // gameStatus == TAILS
backflip++; //Add amount of tails
}
// A try to make an real exit out of a program
if ( choice == 2 )
{
EndProgram( frontflip, backflip, tosses );
}
System.out.println("\nChoose from the menu what you want to do.");
System.out.print("1. Toss the coin\n2. Quit program\n");
choice = input.nextInt();
}
}
//Toss the coin to determine 1 or 2.
public static int Flip()
{
int toss;
toss = 1 + randomNumbers.nextInt( 2 );
if ( toss == 1 )
{
System.out.println("You toss the coin and it lands on head!");
}
else
{
System.out.println("You toss the coin and it lands on tail!");
}
return toss;
}
public static void EndProgram( int frontflip, int backflip, int tosses )
{
System.out.printf("You have tossed %d times.\n", tosses);
System.out.printf("Of all those tosses, %d landed on heads, and %d on tails.\n", frontflip, backflip);
System.exit(0);
}
}
I think I need a do / while loop so that I can have the user answer the yes or no question of do you want to play again? and inside the loop I have a switch statement that also says if the user inputs 0 for the number of flips the program ends?
I thought I could add this snippet to get input:
System.out.println("How many flips do you want?");
System.out.println("(0 will exit the program)");
number = input.nextInt();
I was thinking of creating a new variable and have the user set the number of tosses. Then compound the while loop check like so
while(choice != 0 && numTosses !=0)
and then decrease the count and I'll have to check that count and once it reaches 0 print results as far as how many heads and how many tails then prompt the user if they would like to play the game again but I am having trouble getting the right. honestly I don't even know why I'm trying to do this if but for the knowledge aspect so if you don't wanna help a broski out I understand. I feel like I am on the right track.
You can use 2 loops:
public class CoinFlip {
private enum Coin {
HEADS,
TAILS
};
public static void main(String[] arguments) {
new CoinFlip();
}
CoinFlip() {
Scanner input = new Scanner(System.in);
int heads = 0, tails = 0;
while (true) {
System.out.println("How many flips do you want?");
System.out.println("(0 will exit the program)");
int number = input.nextInt();
if (number == 0)
break; // or System.exit
for (int i = 0; i < number; i++) {
Coin flipResult = flip();
switch (flipResult) {
case HEADS:
heads++;
break;
case TAILS:
tails++;
break;
}
}
System.out.println("Heads: " + heads);
System.out.println("Tails: " + tails);
}
}
private Coin flip() {
return Coin.values()[(int) (Math.random() * Coin.values().length)];
}
}
The while loop continues to ask the user to play again and again, if they put 0 your break it or exit it. In that loop, a for loop will iterate over the flips.

Java passing array error

I've looked around and I can't see why I'm having this problem. Basically, I'm passing an array of player objects but after passing them I can't access the details correctly.
Code:
for(int i = 0; i <= 2;i++){
players[i] = new Player(names[i], chipCount);
System.out.println(players[i].getName());
}
This for loop is in my main method. I have another for loop that sets up three players (Player is an object that requires a name and a number of chips, and has two methods - getName() and getChips()). The players are "Bob" "Billy" and "Barney" and in the above loop they get printed out fine, however when I pass the array of players over to my 'Game' class, attempting to print the player's names in the same way as above just prints "Barney Barney Barney" instead.
Code for Game class:
public class Game {
Player[] players;
int pot = 0;
public Game(Player[] player){
this.players = player;
}
public void startGame(int rounds){
int roundNumber = 1;
while(roundNumber != rounds){
System.out.println("Starting round " + roundNumber);
System.out.print("Players: ");
for(int i = 0; i <= 2; i++){
System.out.print(players[i].getName() + " ");
}
System.out.println("");
roundNumber = rounds;
}
}
}
And how I'm calling Game:
Game game = new Game(players);
Anyone know why it's not printing out the names correctly? Am I passing the array incorrectly?
Thanks
My bet is that the fields (name and chips) in Player are static. They shouldn't.
Read the Java tutorial about instance and static members.

Score calculator

Ok, so, I am very new to java.
I am designing a score calculator, for a project that I have long left aside. Still, I would like to know how to do this, for my own knowledge.
The program is supposed to ask for a dice roll, and add it to the previous rolls, for each player.
I assumed a while loop would accomplish this, but every time it goes through the loop it resets the variable to the current roll. As such, I cannot get a total...
Below is some code:
static int players;
static String p1;
static String p2;
static String p3;
static String p4;
static int maxScore;
static int roll1;
static int roll2;
static int roll3;
static int roll4;
static int total1;
static int total2;
static int total3;
static int total4;
public static void main(String[] args) {
Scanner keyboard = new Scanner(System.in);
System.out.print("Enter number of players: ");
players=keyboard.nextInt();
System.out.print("Enter Maximum Score: ");
maxScore=keyboard.nextInt();
if(players==2){ //will add more ifs when i get the code right
System.out.println("Please enter players names.");
System.out.print("Player 1: ");
p1=keyboard.next();
System.out.print("Player 2: ");
p2=keyboard.next();
System.out.println(p1 + "\t \t " + p2 + "\n"
+ "_______ \t _______ \n" ); //displays scorecard look with players names
{
while (total1 < maxScore && total2<maxScore) {
//scorecard quits when maxScore is reached by either player
int roll;
total1=(roll+roll1);
System.out.print("");
roll=keyboard.nextInt(); //asks for current roll
System.out.print("\n"+"_____"+"\n");
System.out.print(roll+"+"+"\n"+roll1+"\n"+"_____"+"\n"+(roll+roll1)+"\n");
/*i want this to display total score + last roll and then
*total it again on the next line*/
roll1=roll;
}
Some hints for your programming progress in Java:
The variable roll serves no purpose. roll1, and so on, will store the last roll for each player.
Initialize your variables, if possible. Relying on default values should be avoided, as it may bring you problems as you learn (NullPointerException will pay you a visit sometime).
In your loop, you had total1=(roll+roll1);. This is wrong. Your variables, total1, roll, roll1 are not initialized by the time the program reaches this point. As they are integers, they are (silently) initialized to 0, so total1 yields 0 at this point, which does not accomplish much. After this, you proceed to retrieve the roll. Try the other way around, first the roll, then adding up.
You mentioned you're new to Java, but, at some point in the future, you might consider implementing this same program with arrays. You'll notice it saves you much of the repeating code you wrote now.
Summing up, and translating to code guidelines (for 2 players):
public class MyScoreCalculator {
static String p1 = "";
static String p2 = "";
static int maxScore = 0;
static int roll1 = 0;
static int roll2 = 0;
static int total1 = 0;
static int total2 = 0;
public static void main(String[] args) {
Scanner keyboard = new Scanner(System.in);
// Dialogue to get data...
// Display scorecard look with players names
while (total1 < maxScore && total2 < maxScore) {
//scorecard quits when maxScore is reached by either player
roll1 = keyboard.nextInt(); // ask for current roll
System.out.println(total1 + "+");
System.out.println(roll1);
System.out.println("_____");
System.out.println(roll1 + total1);
total1 = total1 + roll1;
// Do the same for next player.
}
}
}
If I am reading your question correctly then the solution is
total1+=(roll+roll1);
which is the same thing as
total1= total1+(roll+roll1);
Your just not adding the rolls to the total value!
Also as a point of note, it is not a good idea to have your instance variables as public and static. It would be better if they were private and not static. For example
private int players;
Hope the answer helps
Your total1 calculation should be total1 += roll and happen after the new roll input. Also if roll1 represents the last roll, name the variable accordingly, it's much more readable.
Since you have many players, try to abstract the concepts and separate the input from the "accounting". For example, you could create a PlayerScore class that holds a total and the last input (and the player's name), with a method that takes care of adding and saving the last input, as well as prettyprinting the infos. You can then have a collection of PlayerScore and iterate over it, ask the current roll and have the infos updated.

Categories