I'm creating a game for homework, and I'm very stuck in the beginning stages. The game takes inputs from two players. The player class controls the guesses by each player. I've been able to correctly set up the player class so that it only accepts the allowed range of inputs.
However, I'm having difficulty calling the guess variable for two player objects. I've tried to determine how to call the value of each guess variable for each object, but it keeps giving me errors. Am I calling the variable correctly? Or is my logic of having two different guesses values for each player object correct? Or is there another way that I need to write the code to have a guess variable for each player?
player class code:
import java.util.Scanner;
public class player {
//handles the input from the player
public player() {
while (true) {
// Prompt the user to guess the number
System.out.println("Enter your guess: ");
Scanner input = new Scanner(System.in);
int guess = input.nextInt();
System.out.println(guess);
if (guess < 0) {
System.out.println("You entered a negative number.
+ "The number you enter must be between 0 and 4. " +
"Please try again. ");
}
else if (guess >= 5){
System.out.println("You entered is greater than 4. "
+ "The number you enter must be between 0 and 4. " +
"Please try again. ");
}
else{
break;
}
} // End of while loop
}//end of player method
}//End of player class
Main code:
public class HW2 {
public static void main(String[] args) {
System.out.println("It's Player A's turn to guess!");
player playerA = new player();
System.out.println(playerA.guess);
System.out.println("It's Player B's turn to guess!");
player playerB = new player();
System.out.println(playerB.guess);
}//end of main
} // end of HW2 class
Thank you in advance for any help!
Declare your guess variable as an instance field instead of a method variable. It's simply a matter of scope
public class player {
int guess;
.....
and instead of int guess = input.nextInt();in the method simply write guess = input.nextInt();
This should solve the call issue
You are trying to access the guess variable outside of its scope (this variable is only accesible in the player method).
In order to fix it, define a public field in the Player class and assign the guess value to it (better use setter and getter). Then you will be able to access it in your main method.
With regards to your initial question, about accessing the "guess" variable for each player:
The guess variable for each player is a local variable declared within the constructor. As such, it can't be seen outside the constructor scope and so when your main method tries to access playerB.guess, the compiler can see that there is no variable called guess in the player class. It doesn't, and can't, realize that you're actually trying to access a local variable inside the constructor. So, to solve this particular problem - you could make the guess variable a field in the player class. e.g.
//handles the input from the player
public player() {
public int guess = 0;
while (true) {
// Prompt the user to guess the number
System.out.println("Enter your guess: ");
Scanner input = new Scanner(System.in);
guess = input.nextInt();
System.out.println(guess);
if (guess < 0) {
System.out.println("You entered a negative number.
+ "The number you enter must be between 0 and 4. " +
"Please try again. ");
}
else if (guess >= 5){
System.out.println("You entered is greater than 4. "
+ "The number you enter must be between 0 and 4. " +
"Please try again. ");
}
else{
break;
}
} // End of while loop
}//end of player method
}//End of player class
This will resolve the particular compile problem - but one thing to note, because the logic for making a guess is in the constructor of the player object, this means it will only be called once, when the class is created.
Related
I need to ask the user for a number of dice to roll, (at least 1) and then loop if necessary to return a positive integer. Simple question, but I'm new to Java and don't understand how to do this using a while loop and bringing my variable back into scope.
Here's what I have so far, as anyone can see my variable 'numOfDice' is never pulled back into scope, as I need it later in my program to establish a variable array length.
while (true) {
System.out.println("Hello! How many dice would you like to roll");
int numOfDice = scan.nextInt();
if (numOfDice<=0) {
System.out.println("Please enter a positive integer and try again");
}else {
break;
}
}
So as you can see my variable is never pulled back into scope, and I've tried initializing it before the while loop, with no luck. I've also tried
System.out.println("Hello! How many dice would you like to roll");
int numOfDice = scan.nextInt();
while (true) {
if (numOfDice<=0) {
System.out.println("Please enter a positive integer and try again");
}else {
break;
}
}
But this results in an infinite loop if a negative number is an input, as my if will repeat forever.
Anyways, I'm very new to Java (my 6th week learning) and any veteran help would be much appreciated. I'm willing to learn new ways to create these loops or tricks to pull variables back into scope (if possible).
Solved. Thanks to tgdavies telling me to split the declaration and assignment I was able to finish this problem. Here's the solution for anyone who stumbles upon this.
System.out.println("Hello! How many dice would you like to roll");
int numOfDice;
numOfDice = scan.nextInt();
while (true) {
if (numOfDice <= 0) {
System.out.println("Please enter a positive integer and try again");
numOfDice = scan.nextInt();
} else {
break;
}
}
This is very simple.
First you have to declare your variable outside the loop.
int numOfDice = -1;
Then you need to think of a way to update the state of your variable numOfDice inside the loop. Hence,
numOfDice = sc.nextInt();
Should be inside your loop. Now, the state of your variable numOfDice is updated. After that we can check if the value is a negative or not, and reiterate the loop accordingly.
Hence, the overall code will look like this.
int numOfDice = -1; //Declaration - value is negative because the while loop has to be executed at least once.
Scanner sc = new Scanner(System.in);
while(numOfDice<=0){ // checks if the variable is negative or positive, loop continues if the value is negative
System.out.println("Hello! How many dice would you like to roll");
numOfDice = sc.nextInt(); //updates the state of the variable
if (numOfDice<=0) {
// this line will be printed only if the value is negative.
System.out.println("Please enter a positive integer and try again");
}
}
Hope this answer is helpful.
Refer this article to understand more about while loops in java.
Let me start by showing my solution first...
public static void main(String[] args) {
Scanner scan = new Scanner(System.in);
System.out.println("Let's start rolling some dice");
while (true) {
System.out.println("Hello! How many dice would you like to roll");
int numOfDice = scan.nextInt();
if (numOfDice < 0) {
System.err.println("Please enter a positive integer and try again");
} else if (numOfDice == 0) {
System.out.println("Goodbye!");
break;
}
}
scan.close();
}
As you can see, it is not much of a variation, but it has clear boundaries. For example, you can't have a negative number of dice rolled. So checking for the number of dice to be less than zero (negative) is an error and an appropriate message is shown when that condition is reached.
The second thing you see is a clear case for ending the "forever" loop. And that is when zero is passed through the Scanner object. Not much of an explanation required. Pass zero and simply break out of the loop.
The rest, if a positive integer is passed, keep rolling the dice!
Output sample
Let's start rolling some dice
Hello! How many dice would you like to roll
2
Hello! How many dice would you like to roll
3
Hello! How many dice would you like to roll
9
Hello! How many dice would you like to roll
-3
Please enter a positive integer and try again
Hello! How many dice would you like to roll
-2
Please enter a positive integer and try again
Hello! How many dice would you like to roll
1
Hello! How many dice would you like to roll
3
Hello! How many dice would you like to roll
0
Goodbye!
...to return a positive integer
Sorry for the dramatic heading, but I miss this from the OPs question the first time I read it. The code above keeps rolling until the user enters zero. Let's modify this so that it returns a positive integer.
public static void main(String[] args) {
Scanner scan = new Scanner(System.in);
System.out.println("Let's start rolling some dice");
while (true) {
System.out.println("Hello! How many dice would you like to roll");
int numOfDice = scan.nextInt();
if (numOfDice < 0) {
System.err.println("Please enter a positive integer and try again");
} else if (numOfDice == 0) {
System.out.println("Goodbye!");
break;
} else {
// Add some code here (i.e. a Random generation of dice values 1-6)
System.out.println("You rolled a " + diceRollValue);
break;
}
}
scan.close();
}
Variable Scope
Since the OP seems to struggle with issues related to scope, I will expand on this answer to focus on scope. Good coding practices call for minimizing the scope of variables. This means (in theory):
No global variables, period!
Local variables should be declared at the lowest possible block.
Variables shall be declared as close to the point of usage as possible.
Of course, in practice, global variables are often necessary. But what no developer should do is declare global variables by default. Instead, all variables shall be declared at the lowest levels of the code, and then "bubbled up" as needed and stop "bubbling" them up when the desired accessibility is reached. Let's look at an example from this code.
The variable numOfDice is declared inside the while loop. This is the lowest level where this variable can be declared. Since the variable is used at the top of the loop, it is OK to declare it and assign a value in the same line. The question is, should this variable be declared outside the loop? The answer is yes, for a very specific reason.
Creating a "forever" loop while(true){...} may not be a good idea. IN FACT, it can be argued that putting the break condition there might be a better coding practice than to include the break condition inside the loop. So, for this reason (and improving readability of the code as well), we might be better off setting the the variable outside the loop to a value, and then prompt the user to enter the number of rolls inside the loop like this:
System.out.println("Let's start rolling some dice");
int numOfDice = -1;
while (numOfDice != 0) {
System.out.println("Hello! How many dice would you like to roll");
int numOfDice = scan.nextInt();
...
}
Setting the value to -1 allows the instruction pointer to enter the loop because the evaluation of numOfDice returns true. Once inside the loop, it will continue to iterate until the evaluation returns false; and this is when the user enters 0. In the original code, negative values prompt an error message. Negative and positive values continue the "game". This is perfectly fine. As to the improved readability, when you see while (numOfDice != 0) the intent is clear; much better than to "hide" the break condition inside the loop. If the loop contain a lot of lines of code, the break condition is harder to find. So, in the end, this is a better solution.
An alternative is to use a do...while loop. This is the preferred structure when the intent is for the loop to run at least once. This is possible because the break condition is evaluated at the end of the loop rather than at the beginning in a conventional while loop. The equivalent do...while loop is as follows:
System.out.println("Let's start rolling some dice");
int numOfDice = 0; // initialize to the break condition value (just in case)
do {
System.out.println("Hello! How many dice would you like to roll");
int numOfDice = scan.nextInt();
...
} while (numOfDice != 0);
The last thing with regards to scope. I mentioned before that variables should be declared as close to the point of usage as possible. This means that instead of this
public void myMethod() {
int myVariable = 0
.
.
.
.
.
myVariable = someCodeThatSetsValue();
.
.
}
You should do this instead to follow best practices
public void myMethod() {
.
.
.
.
.
.
int myVariable = someCodeThatSetsValue();
.
.
}
I'm struggling with dealing of inventory scan for my game, it basically search for the user inventory if "Flying Broom" if present(it was collected in another method and upload the code is too long), if not it will run the method challengedragon() again; else, it will proceed to the next challenge if the item is present.I was think of inserting method as parameter but it is not possible. This is what I have now. :
public class Main {
String Flyingbroom = "Flying broom";
public static void main(String[] args) {
Player_inventory p = new Player_inventory();
challengedragon();
}
public void challengedragon() {
System.out.println("a Hungarian Horntail dragon! Let's start the battle! You have four options to beat the dragon: ");
System.out.println("1: Fly away with your broom");
System.out.println("2: Fight the dragon");
System.out.println("3: Just run to the egg and get it");
System.out.println("4: Hide behind a rock");
System.out.println("5: Go back to Hogwart");
System.out.println("Your choice is: ");
Scanner in = new Scanner(System.in);
int dragonfightchoice = in .nextInt();
if (dragonfightchoice == 1) {
{
p.Scanitem(Flyingbroom,
"Good choice! You managed to kill the Hungarian Horntail dragon and to get the golden egg",
"You dont have the broom. Try to search for the broom",
playerHP);
proceedtonextchallengelake();
} else if (dragonfightchoice == 2) {
System.out.println("The Hungarian Horntail dragon fired you. - 70HP. ");
playerHP -= 70;
challengedragon();
} else if (dragonfightchoice == 3) {
System.out.println("Bad idea... You lose 100 HP");
playerHP -= 100;
challengedragon();
} else if (dragonfightchoice == 4) {
System.out.println("The dragon found you. You lose 30 HP");
playerHP -= 30;
challengedragon();
} else if (dragonfightchoice == 5) {
Hogwart();
} else {
invalid();
challengedragon();
}
}
For my inventory class:
public void Scanitem(String item, String trueouputext, String textifconditionisnotmet) {
if (inv.contains(item) == true) {
System.out.println(trueouputext);
} else if (inv.contains(item) == false) {
System.out.println(textifconditionisnotmet);
}
public static ArrayList<String> inv = new ArrayList<String>();
Do you guys have any recommendation?
Are there additional steps to populate the inventory (variable inv)?
Also, wouldn't you want ScanItem to answer true or false, depending on whether the item was found? Then you would have something like this:
public boolean scanitem(String item) {
return ( inv.contains(item) );
}
if ( p.scanItem(flyingBroom) ) {
System.out.println("Good choice! You managed to kill the Hungarian Horntail dragon and to get the golden egg");
} else {
System.out.println("You dont have the broom. Try to search for the broom");
}
That will get you closer to what you want. However, there are two other issues which you'll need to put into your code:
You will need a loop of some sort, instead of calling challengeDragon from inside of itself.
Somehow, the return value from scanItem must be used to decide whether to loop.
Currently, you do a nested call of a method each time the player does something, this means that sooner or later you'll run out of the stack. A better idea for the framework for your text-based adventure is to have some kind of a description of the current game's state. The state could be represented as an object that contains the following information:
where's the player currently at (on which step, at which "crossing" etc.)
the player's stats (HP, available skills etc.)
the contents of the player's inventory
some previously made choices affecting the game
Then, the code could be written as a simple loop that does the following:
process player's input
change the state according to the player's input
present the player with available options according to the new state
wait for the next input
repeat
I'm really scratching my heard on this one. I'm new at java, and I'm having the strangest thing happen.
It's homework and I'm taking it one step at a time. My issue is the loop just keeps going and stops asking for input, just keeps looping until it terminates. My comments are largely for myself. I tried to extract what was causing my problem and post it here.
Look at the "hatColor" switch, you'll notice the way I'm making sure the user enter only from the options I have allotted. Should I be using a exception handler or something?
Anyway, in short, the problem is that if I enter something with spaces, the loop skips asking for my next input. Like, if I entered "y y y y y " to the scanner when first prompted, the program will terminate and not give me the chance to enter something else.
Please, anyone that understands this, I would really appreciate your help.
import java.util.Scanner;
public class Testing
{
static String hatColor;
public static void main(String[] args) {
gameStart();
}
public static void gameStart()
{
Scanner userInput = new Scanner(System.in);
boolean keepLooping = true;
int loopCounter = 0;
System.out.println("The game begins. You must choose between 3 different colored hats."
+ " You can type white, black, or gray.");
while (keepLooping == true)
{
hatColor = userInput.next();
switch(hatColor)
{
case "white":
System.out.println("You have chosen the path of well intentioned decisions.");
walletDrop();
//the two items below are only there in case the wallet drop somehow completes without calling another method
keepLooping = false; // stops the while loop from looping again.
break; // breaks out of the switch
case "gray":
System.out.println("You have chosen the path of free will.");
walletDrop();
keepLooping = false;
break;
case "black" :
System.out.println("You have chosen the path of personal gain.");
walletDrop();
keepLooping = false;
break;
default : //we could just copy this default chunk for later switch statements
if (loopCounter >= 3)//end program on them
{
System.exit(0);
}
System.out.println("You didn't enter a usable answer. Try again");
loopCounter++;
if (loopCounter == 3)
{
System.out.println("This program will self destruct if you enter another invalid response.");
}
}//end of switch
}//end of while
}//end of game start method
public static void walletDrop()
{
System.out.println("wallet drop successful");
}
}
So I have actually solved this right after posting. In case someone else needs to look here for help:
The issue I was experiencing was due to using the scanner method
variableToAssign = scannerName.next();
instead of
variableToAssign = scannerName.nextLine();
I'm trying to write a black jack program in Eclipse and I'm having an issue when the program deals an Ace. I asked the user if they want the Ace to be worth 1 or 11. It does that, but when I type in a value, it gives an error message
"Exception in thread "main" java.lang.StringIndexOutOfBoundsException: String index out of range: 0
at java.lang.String.charAt(Unknown Source)
at PlayBlackJack.main(PlayBlackJack.java:72)"
Could someone help with that? I have a separate class that if the random card generated is an ace, it returns the value of 11. Here's that part of the code
Update: It adds the value of the Ace to the user's total. But after an Ace is dealt and the user chooses a value, no matter what the total is, it stops the users turn and goes to the dealer. How can I correct this? Also another issues I am having is After the user says 'no' to wanting another card, it goes to the dealer and works fine, but then when asking the user if they want to play again, it goes into an infinite loop and starts throwing out random cards. How can I correct this issue also?
import java.util.Scanner;
public class PlayBlackJack {
public final static int MAXCARDS=52;
//declaring the constant maxcards to be 52
//since there are 52 cards in the deck
public static void main(String[] args) {
Scanner kbd=new Scanner (System.in);
String printRules;
//check to see if the user wants to see the rules or not
String more;
//variable used to see if the user would like to play the game
String next;
//variable used to see if the user would like another card
int dealerTotal, userTotal;
//keeps track of the user's total and the dealer's total
int wins=0, losses=0;
//variables used to keep track of the user's wins and losses
int card = 0;
System.out.println(" Welcome to Black Jack!");
System.out.println("Would you like to see the rules? Type yes or no");
//If yes, rules printed, if no, rules not printed
printRules=kbd.nextLine();
printRules=printRules.toUpperCase();
if (printRules.charAt(0)=='Y')
{
(print rules)
System.out.println("Now lets play!\n\n\n");
}
System.out.println("Would you like to play a game of Black Jack?");
more=kbd.nextLine();
more=more.toUpperCase();
next="Yes";
while (!more.isEmpty() && more.charAt(0)=='Y')
{
System.out.println("The game begins with this your first card:");
userTotal=0;
dealerTotal=0;
while (!next.isEmpty() && next.charAt(0)=='Y')
{
card=PickACard.findCardValue();
if (card==11)
{
System.out.println("Would you like the Ace to be a 1 or 11?");
int aceValue=kbd.nextInt();
while (aceValue!=1 && aceValue!=11)
{
System.out.println("You did not enter a 1 or 11");
aceValue=kbd.nextInt();
}
card=aceValue;
}
userTotal=userTotal+card;
System.out.println("You're total is " +userTotal);
if (userTotal>21)
{
System.out.println("Sorry, You lose");
losses++;
System.out.println("Would you like to play again?");
next="No";
more=kbd.nextLine();
more=more.toUpperCase();
}
else
{
System.out.println("Would you like another card?");
next=kbd.nextLine();
next=next.toUpperCase();
}
}
while (dealerTotal<=userTotal && userTotal<21)
{
System.out.println("Now it's the dealer's turn");
int card1=0;
card1=PickACard.findCardValue();
if (card1==11)
{
int aceValue1;
if (dealerTotal+11>21)
{
aceValue1=1;
}
else
{
aceValue1=11;
}
card1=aceValue1;
}
dealerTotal=dealerTotal+card1;
System.out.println("The dealer's total is "+dealerTotal);
if (dealerTotal==userTotal && userTotal<21)
{
losses++;
System.out.println("Sorry, you lose. Would you like to play again?");
more=kbd.nextLine();
more=more.toUpperCase();
}
if (dealerTotal>21)
{
wins++;
System.out.println("You Win! Would you like to play again?");
more=kbd.nextLine();
more=more.toUpperCase();
}
/*else
{
losses++;
System.out.println("You lose. Would you like to play again?");
more=kbd.nextLine();
more=more.toUpperCase();
}*/
}
}
System.out.println("You won "+wins+" game(s) and lost "+losses+" game(s)");
kbd.close();
}
}
I think that because you are using kbd.nextInt() to get the Ace value there is a new line character is left in the buffer so when the loop goes around kbd.nextLine() returns new line character and not Y that might be causing an issue with more.charAt(0) You might have to add an extra kbd.nextLine(); to get rid the new line character. Also as Elliot Frisch pointed out you should check if the string is empty in the while control statement.
while(!more.isEmpty() && more.charAt(0) == 'y')
{
}
I guess next.charAt(0) is showing the error. You can try to do kbd.nextLine(); right before you ask would you like another game and also check if next is not empty.
while(!next.isEmpty() && more.charAt(0) == 'y')
{
}
Try this
System.out.println("Sorry, You lose");
losses++;
System.out.println("Would you like to play again?");
next="No";
kbd.nextLine(); // to flush out new line character
more=kbd.nextLine();
more=more.toUpperCase();
You can also use nextLine() and parse it to int that will avoid the new line character issue.
aceValue = Integer.parseInt(kbd.nextLine());
I can't tell which line is line 72 of your code, but I can tell you that it's pretty likely based on what you've given us that somehow either your more or next variables are becoming empty strings (i.e. ""). If you try and call charAt(0) for a 0-length String, you'll get a StringIndexOutOfBoundsException.
Ok, I am having a problem receiving a value... I have been researching for several days, but nothing has hit the topic I need. It is a mastermind game. I am creating this for a Final project in my High School programming class. The Eclipse Compiler is telling me that in cannot be resolved. How do I fix this and Accomplish my goal. This is not being run in an applet.
package masterMind;
import java.util.Scanner;
public class MasterMind {
public static void main(String[] args) {
System.out.println("This is MasterMind, a logic game");
System.out.println("To win you must guess correctly where each number is");
System.out.println("You will be told if you get one correct");
System.out.println("You will only get 10 tries, then you lose");
System.out.println("Lets begin");
//Change this value to change the game
int m1=2;
int m2 =3;
int m3=2;
int m4=1;
//Create Board
System.out.println("__ __ __ __");
Scanner UserGuess = new Scanner(System.in);
int num = in.nextInt();
I have very limited Coding knowledge, so please keep it simple and explain
System.in is the InputStream of the system (like the cmd for windows) , in order to read from that you use the Scanner or InputStreamReader just like you are trying to do ... so instead of
in.nextInt();
you need
userGuess.nextInt();
and btw learn to use capital letters properly as it will help you later , like userGuess should not start with a capital since its an instance not a class.
anyways , for your game you have to guess 10 times which means you have to repeat the same guessing action 10 times or till the user guesses all the numbers , thats when you should use a while loop like so ....
boolean guessedAll = false;
int guessedCount=0;
int tryCounter=0;
while(tryCounter<9 || !guessedAll){
//read the number from the user and test it ...
//if number equals one of the numbers above then guessedCount++ ...
//if guessedCount==4 then guessedAll=true
tryCounter++;
}
now i almost gave you all of the algorithm needed to do that homework , but i ain't going to solve it for you till you try , else you will learn nothing ;)
you could ofcourse ask for help as comment after you've tried some ... good luck
for nextInt method you should call it from Scanner object
Change this
int num = in.nextInt();
To
int num = UserGuess.nextInt();
You never closed the brackets when you started the class nor when you started the main method. Match every { with a }.
package masterMind;
import java.util.Scanner;
public class MasterMind {
public static void main(String[] args) {
System.out.println("This is MasterMind, a logic game");
System.out.println("To win you must guess correctly where each number is");
System.out.println("You will be told if you get one correct");
System.out.println("You will only get 10 tries, then you lose");
System.out.println("Lets begin");
//Change this value to change the game
int m1=2;
int m2 =3;
int m3=2;
int m4=1;
//Create Board By randomly generating the number
//After generating the code, print the blank board to start the game
System.out.println("__ __ __ __");
//Take in the user's guess (limit is 10)
int limit = 10
for(int i = 0; i < limit; ++i) {
Scanner UserGuess = new Scanner(System.in);
int num = in.nextInt();
//Other logic..Leaving it for you to attempt
}
}
You want to make a program which the user must guess where each number is in a 4 digit code.. Well how do you do this?
We need the user to be able to input a number, typically the rules of this game are:
There are 6 possible numbers or colors
The code is 4 numbers or colors long
The user has ten tries to guess the code correctly
That means we have to start by doing something like this.
Generate the 4-digit code somehow (with the possible combinations from 0000-6666) and the split the random number put it in an array
Ask the user to enter a number guess along with a position for that number
Keep checking the user guess against the code, each time display the current guesses and which ones they have correct