How to make changes to a created object in Java - java

The following code works all the way up until where the user enters the score for the team int homeScore = input.nextInt(), at which point the compiler returns the following error code:
Exception in thread "main" java.util.NoSuchElementException
at java.util.ArrayList$Itr.next(ArrayList.java:854)
at assignment.PremierLeagueManager.main(PremierLeagueManager.java:121)
Java Result: 1
Any idea's on how to fix this?
boolean validHome = false;
boolean validAway = false;
System.out.println("Enter name of Home team: ");
String homeName = input.next();
Iterator<FootballClub> it = premierLeague.iterator();
while (it.hasNext()) {
if (it.next().getClubName().equals(homeName)) {
validHome = true;
}
}
System.out.println("Enter name of Away team: ");
String awayName = input.next();
Iterator<FootballClub> it2 = premierLeague.iterator();
while (it2.hasNext()) {
if (it2.next().getClubName().equals(awayName)) {
validAway = true;
}
}
if (validHome == true && validAway == true) {
System.out.println("Enter number of goals scored by " + homeName + ":");
int homeScore = input.nextInt();
int x = premierLeague.indexOf(it.next());
premierLeague.get(x).setGoalsScored(homeScore);
System.out.println("Enter number of goals scored by " + awayName + ":");
int awayScore = input.nextInt();
int y = premierLeague.indexOf(it2.next());
premierLeague.get(y).setGoalsScored(awayScore);
} else {
System.out.println("One of the teams are invalid. Please try again");
}

At the top where you do "while (it.hasNext())", this loops until the iterator has no more items, so when you get to "int x = premierLeague.indexOf(it.next());", there is no next item for the iterator, so you get no such element. If you want to start over, you need to create a new iterator.

You're calling it.next() after the call to input.nextInt(), but there is no guarantee that there is any member in the iterator it. I'm not sure this is the problem, but it looks like it.
You don't tell us what the line numbers of your source is, and it is confusing that you say this is a compiler error when it looks like it is a runtime error. But that looks like an error, in any event (and you do that twice).

Related

java.lang.NumberFormatException error after inputting a number [duplicate]

This question already has answers here:
Scanner is skipping nextLine() after using next() or nextFoo()?
(24 answers)
Closed 2 years ago.
I am feeling quite stupid at this point for not being able to figure out something that is most likely a simple fix. I keep getting the error "Exception in thread "main" java.lang.NumberFormatException: For input string: ""
at java.base/java.lang.NumberFormatException.forInputString(NumberFormatException.java:68)
at java.base/java.lang.Integer.parseInt(Integer.java:662)
at java.base/java.lang.Integer.parseInt(Integer.java:770)
at searchSorting.main(searchSorting.java:15)" after inputting how many numbers I want to input. Others solutions to this problem just don't seem to apply to me somehow. Thanks for the help
import java.util.Scanner;
import java.util.Arrays;
public class searchSorting
{
public static void main (String[]args)
{
String line;
int number, search, item, array[], first, last, middle;
Scanner in = new Scanner(System.in);
System.out.print("How many numbers you want to input?: ");
number = in.nextInt();
array = new int [number];
item = Integer.parseInt(in.nextLine());
double[] values = new double[item];
for (int i = 0; i < values.length; i++) {
System.out.print("Input number " + i + ": ");
values[i] = Double.parseDouble(in.nextLine());
}
for (int index = 0; index < 5; index++)
System.out.print(values[index] + " ");
in.nextLine();
Arrays.sort(values);
System.out.println("Sorted number is: " + Arrays.toString(values));
System.out.println("Enter the number you are looking for?");
search = in.nextInt();
first = 0;
last = (item - 1);
middle = (first + last)/2;
while( first <= last )
{
if ( array[middle] < item )
first = middle + 1;
else if ( array[middle] == item )
{
System.out.println(item + " found at location " + (middle + 1) + ".");
break;
}
else
{
last = middle - 1;
}
middle = (first + last)/2;
}
if ( first > last )
System.out.println(item + " is not found.\n");
}}
For more info check out Scanner and Integer documentation, it's an excellent resource.
Edit: Try removing line 15 and replacing item with number in the next line
You call this:
number = in.nextInt();
Assuming the user types 123 and ENTER, this call consumes the 123 and leaves the input stream positioned before the end-of-line character.
The next relevant code is
item = Integer.parseInt(in.nextLine());
The nextLine call advances the input stream past the end-of-line, returning all characters it passed on the way. Since the ENTER key was pressed immediately after 123, the returned value is the emoty string. Which is not an integer.
You need to review your strategy of sometimes scanning numbers (nextInt) and sometimes scanning rest-of-linr (nextLine). Mixing the two needs to be done quite carefully. You might be better advised to stick to the numerical methods (nextInt/nextDouble).
For example, replacing this
item = Integer.parseInt(in.nextLine());
by this
item = in.nextInt();
automatically handles the line-ending.
From discussion in comments:
I am still confused as to why it's having me input
the value a second time on the next line
Making assumptions about how you modified the code since your initial question: it's because you've written code that reads the number twice:
System.out.print("How many numbers you want to input?: ");
number = in.nextInt(); // **** first input ****
array = new int [number];
item = in.nextDouble(); // **** second input ****
double[] values = new double[item];
Each time you call for in.nextSomething() the Scanner is going to read more input. It should likely just be this:
System.out.print("How many numbers you want to input?: ");
number = in.nextInt();
array = new int [number];
double[] values = new double[number];

Is there any way to pass a mutator method as an argument to another method?

I'm creating a text based game, I have a class made for the main character so you can set the characters name, etc. What I'm trying to figure out is, is there any way to pass a mutator (character.setname(input)) as an argument to another method. When I try to do it I'm told that I can't use a void type as an argument to a method. When I was writing out the code for the user to enter their name, and everything else it was repetitive with the error checking so I wanted to create my own method I could call that would error check for me. A couple sentences use the setname method to reset the name if it was entered incorrectly but I can't directly use setname in the error checking method because it's going to be using the same method to check other inputs of data.
Is there any way around this?
Here is the code as requested: I indeed may be overcomplicating the problem, I'm pretty new to java so I'm still learning.
The following code is the code I use to check if the user entered something correctly, it accepts an array which contains all the possible correct answers the user can type in, I've tried to design it in a way that I can error check anything with it, not just "yes" or "no" statements, getVariable is the accessor method, and setVariable is the one I'm trying to get to work, I'm trying to pass the mutator as well so I can reset the error
public void confirmEntry(String question, String[] options, String getVariable, setVariable) throws InterruptedException
{
boolean correctEntry = false;
System.out.print("Is this correct? ");
for(int i = 0; i < options.length - 1; i++)
{
System.out.print(options[i] + ", ");
}
System.out.print("or ");
System.out.print(options[options.length - 1] + ": ");
input = in.nextLine();
for(int i = 0; i < options.length; i++)
{
if(input.equals(options[i]))
{
correctEntry = true;
System.out.println(correctEntry);
}
}
System.out.println(correctEntry);
while(correctEntry == false)
{
Thread.sleep(2000);
System.out.print("You must enter ");
for(int i = 0; i < options.length - 1; i++)
{
System.out.print("\"" + options[i] + "\", ");
}
System.out.print("or ");
System.out.print("\"" + options[options.length - 1] + "\" to continue: ");
Thread.sleep(2000);
System.out.println();
System.out.println("You chose " + getVariable);
Thread.sleep(2000);
System.out.print("Is this correct? ");
for(int i = 0; i < options.length - 1; i++)
{
System.out.print(options[i] + ", ");
}
System.out.print(" or ");
System.out.print(options[options.length - 1] + ": ");
input = in.nextLine();
for(int i = 0; i < options.length; i++)
{
if(input.equals(options[i]))
{
correctEntry = true;
}
}
}
}
The following code is what is currently in the method where you enter information about the character. I'm trying to move more of the code into the error checking method so that each time I ask the user a question, name, age, etc. I just simply need to call the method.
public void characterCreation() throws Exception
{
//create an instance of the class player (your character creation)
Player character = new Player();
//Initial Introduction to the game
System.out.println("Welcome to Stranded!");
Thread.sleep(2000);
System.out.println("Tell us a little about yourself!");
Thread.sleep(2000);
//______________________________________________________________________________________________________________
//SET YOUR CHARACTER'S NAME
String[] yesNo = {"yes", "no"}; //array to feed into confirmEntry method
System.out.print("Enter your character's name: ");
input = in.nextLine(); //asks for input of the name
character.setName(input); //sets name in the player class
System.out.println("You chose " + character.getName()
+ " for your character's name");
Thread.sleep(2000);
confirmEntry("Enter your character's name: ", yesNo, character.getName(), character.setName(input));
while(input.equals("no"))
{
Thread.sleep(2000);
System.out.print("Enter your character's name: "); //prompt to enter name again
input = in.nextLine();
character.setName(input); //sets name in player class
Thread.sleep(2000);
System.out.println("You chose " + character.getName()
+ " for your character's name"); //confirms what user entered for name
Thread.sleep(2000);
confirmEntry("Enter your character's name: ", yesNo, character.getName(), character.setName(input));
}
I'm trying to move more code after the SET CHARACTER NAME comment into the confirmEntry method, however the rest of the code involved with the character's name uses the mutator to set the name. That's the problem. I wanted to try to get as much code into confirmEntry as possible so whenever I ask the user to enter something about their character I basically just have to call the method.
If you are using java 8 you can create your method with a method reference param :
public void functionName(Consumer<String> setter){setter.
accept(string);}
and to call your method you can use : functionName(character::setname);
you can see : http://www.informit.com/articles/article.aspx?p=2171751&seqNum=3
What is an entry? It appears to be some value that the user has entered.
class Entry{
String value;
public Entry(String value){
this.value = value;
}
public boolean confirm(String input){
return value.equals(input);
}
}
How about you store all of your entries.
Map<String, Entry> entries = new HashMap<>();
String message = "Enter your character's name: ";
System.out.println(message);
String input = in.nextLine();
entries.put(message, new Entry(input));
Now when you want to confirm.
public void confirmEntries(){
for(String message: entries.keySet()){
System.out.println(message);
System.out.println(entries.get(message) + "yes/no?");
//get some input and update the value. etc.
}
}
Another way to do it would be to create a Runnables.
List<Runnable> entryRunnables = new ArrayList<>();
Then anytime you want to add an action.
Runnable r = ()->{
System.out.println("Enter your players name, yes/no");
String input = in.readLine();
//check input and do stuff.
}
entryRunnables.add(r);
Now to check entries. (stream method)
entryRunnables.forEach(Runnable::run);
Or
for(Runnable r: entryRunnables){
r.run();
}

What am I missing here? Looping with dialog boxes

I am not sure why this code is not working.
I am suppose to have another dialog box appear after the user selects yes or no, but whenever I run the program, it asks for y or no and then nothing happens after.
Any ideas on what I need to do?
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
int max = 0;
int min = Integer.MAX_VALUE;
String number;
boolean yn = true;
do {
number = JOptionPane.showInputDialog("Please enter a number");
int num = Integer.parseInt(number);
if (num > max) {
max = num;
}
if (num < min) {
min = num;
}
System.out.println(min + " " + max);
JOptionPane.showInputDialog("Would you like to enter another number? (y/n)");
String ny = in.nextLine();
if (ny.equals("n")) {
yn = false;
}
JOptionPane.showInputDialog(ny);
} while (yn == true);
JOptionPane.showMessageDialog(null, "The max number is " + max + " and the mininum number is " + min);
}
}
The program stops on
String ny = in.nextLine();
waiting for input from System.in based on the Scanner defined on the first line.
If you enter 'n' on the console and press enter then the program carries on and shows the next dialog box.
I guess you meant to say:
String ny = JOptionPane.showInputDialog("Would you like to enter another number? (y/n)");
The issue you are having is that you are not accepting the input from the panel, and are instead taking it from the console. To solve this, set ny to be equal to the input from the JPane, like so:
String ny = JOptionPane.showInputDialog("Would you like to enter another number? (y/n)");
However, there is another issue, which is this line:
JOptionPane.showInputDialog(ny);
It creates a pane that you don't need that displays y or n, and doesn't accept input. This line doesn't need to be there, so you should remove it. Your code works fine otherwise.

System.out.println does not work [duplicate]

This question already has answers here:
How to test for blank line with Java Scanner?
(5 answers)
Closed 7 years ago.
I am beginner in learning java programming. Basically, I can't make the last bit of my code to work. Before I show you my code, I think it is a good idea to show how the result should be. The result of the program should be:
Please Enter either S(supply) or R(replenish) followed by ID and quantity.
R p122. 10
New Stock-level for p122(Chain) is 58
S. p124. 20
New Stock-level for p125(Pedal) is 18
S. p905. 20
No part found with ID p905
.....// enter empty string to terminate
//Show final stock levels of all Parts
Although, I did be able to perform the main calculation and everything, I cannot print out the final stock levels of all Parts. I really don't understand why.
Here is my code:
import java.util.Scanner;
public class TestPart {
public static void main(String[] args) {
// Array of 5 Part objects
// Part[] part = new Part[5];
Part[] part = new Part[5];
part[0] = new Part("p122", "Chain", 48, 12.5);
part[1] = new Part("p123", "Chain Guard", 73, 22.0);
part[2] = new Part("p124", "Crank", 400, 11.5);
part[3] = new Part("p125", "Pedal", 3, 6.5);
part[4] = new Part("p126", "Handlebar", 123, 9.50);
///////// Test Class 2 ////////
Scanner scanner = new Scanner(System.in);
System.out.println("Please Enter either S (supply) or R (replenish) followed by ID and quantity.");
while (scanner.hasNext()) {
String sOrR = scanner.next();
String inputId = scanner.next();
int amount = scanner.nextInt();
for (int i = 0; i < 5; i++) {
String id = part[i].getID();
// Find ID in array
if (id.equals(inputId)) {
// S or R
if (sOrR.equals("R")) {
part[i].replenish(amount);
} else {
part[i].supply(amount);
}
System.out.println("New Stock-level for " + part[i].getID() + "(" + part[i].getName() + ") is "
+ part[i].getStockLevel());
}
}
if ((inputId.equals(part[0].getID()) == false) && (inputId.equals(part[1].getID()) == false)
&& (inputId.equals(part[2].getID()) == false) && (inputId.equals(part[3].getID()) == false)
&& (inputId.equals(part[4].getID()) == false)) {
System.out.println("No part found with ID " + inputId);
}
}
scanner.close();
System.out.println("Final stock level for all the parts: ");
for (int i = 0; i < 5; i++) {
System.out.println("Final Stock-level for " + part[i].getID() + "(" + part[i].getName() + ") is "
+ part[i].getStockLevel());
}
}
}
My program executes perfectly the calculating part. However it doesn't display final stocklevels.
Please Enter either S(supply) or R(replenish) followed by ID and quantity.
R p122. 10
New Stock-level for p122(Chain) is 58
S. p124. 20
New Stock-level for p125(Pedal) is 18
S. p905. 20
No part found with ID p905
Your abort condition (namely scanner.hasNext()) won't exit the while loop whenever the user enters an empty string. I don't know if you already noticed but whenever the user only hits the return key, nothing happens because Scanner.next does not trigger on return only. Though be aware that it stores your input. That means once you enter a "valid" input (such as abc), the Scanner will give you everything the user just entered before that valid input. Just a small example to demonstrate what I mean:
Scanner scanner = new Scanner(System.in);
while(scanner.hasNext()) {
System.out.println("\"" + scanner.next() + "\"");
}
scanner.close();
System.out.println("finished");
So, if you want to abort your program after the user entered an empty line, this is not possible with java.util.Scanner.hasNext. I recommend you add another character to your "S or R" option that allows the user to exit the program like this:
if(sOrR.equals("E")) break;
You should place this directly behind String sOrR = scanner.next();.

Basic parallel array with two Strings

When I test it, it builds fine. But when I run it only the intro and user output questions come up (which is what it's supposed to do), but when I input an answer an error comes up:
Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: 50
at statecapitals.StateCapitals.main(StateCapitals.java:141)
Now I know i'm new at this but what I think the error is, is that my arrays are not corresponding and i'm not sure what I did wrong. Any help would much appreciated. Here is what I have:
String[] stateName = new String[50];
String[] capName = new String[50];
int i;
for(i=0; i < 50; i++)
{
stateName[0] = "Alabama";
stateName[1] = "Alaska";
.....
capName[0] = "Montgomery";
capName[1] = "Juneau";
.....
}
boolean found = false;
Scanner keyboard = new Scanner(System.in);
System.out.println("This program is designed...");
System.out.println("Please enter the name of a U.S. state (please enter capitalized):");
stateName[i] = keyboard.nextLine();
for(i=0; (!found) && (i < stateName.lenth); i++)
if(stateName[i].matches(capName[i]) )
System.out.print(The capital of " + stateName + " is " + capName);
found = true;
if(!found)
System.out.println("The name you entered was not on the list.");
*Updated & edited:
the line of code that was having the most trouble was:
stateName[i] = keyboard.nextLine();
Thank you for everyone's help, i've made some changes:
int i;
for(i=0; i < 49; i++)
{
stateName[i+1]
.....
capName[i+1]
...
}
Plus I added the curly brackets to my for loop at the bottom. Now when I run it, it stops on the line:
if(capName[i].matches(stateName[i]) )
and the error this time is:
Exception in thread "main" java.lang.NullPointerException
at statecapitals.StateCapitals.main(StateCapitals.java:146)
Thank you again for everyone's input.
Since i is not initizalized (in the snippet)
stateName[i] = keyboard.nextLine();
should be something like:
searchState = keyboard.nextLine();
And this comparison is pointless since it would never match (should be searchState from above):
if(stateName[i].matches(capName[i]) )
problem 1
stateName[i] = keyboard.nextLine();
problem 2
for(i=0; i < 50; i++)
{
stateName[0] = "Alabama";
stateName[1] = "Alaska";
.....
capName[0] = "Montgomery";
capName[1] = "Juneau";
.....
}
i think this should be stateName[i] = "Alabama";
Problem 3
You missed the "{" "}" in the for loop
for(i=0; (!found) && (i < stateName.length); i++){
if(stateName[i].matches(capName[i]) ){
System.out.print(The capital of " + stateName + " is " + capName);
found = true;
}
}
if(!found)
System.out.println("The name you entered was not on the list.");
You've had a lot of good suggestions to improve your code that I would try to implement.
The reason for the error is your for loop.
for(i=0; (!found) && (i < stateName.lenth); i++)
The length of the array is going to return 50, but your indexes go from 0 - 49 and because you never find a match, it goes through the whole loop.

Categories