Welcome to the Treehouse Community
Want to collaborate on code errors? Have bugs you need feedback on? Looking for an extra set of eyes on your latest project? Get support with fellow developers, designers, and programmers of all backgrounds and skill levels here with the Treehouse Community! While you're at it, check out some resources Treehouse students have shared here.
Looking to learn something new?
Treehouse offers a seven day free trial for new students. Get access to thousands of hours of content and join thousands of Treehouse students and alumni in the community today.
Start your free trialNick Fite
11,168 PointsGot an index out of bounds exception trying to run the game
Hey guys, I got an index out of bounds exception trying to run the game with the code from this exercise:
Exception in thread "main" java.lang.StringIndexOutOfBoundsException: String index out of range: 116
at java.lang.String.charAt(String.java:658)
at Game.applyGuess(Game.java:39)
at Prompter.promptForGuess(Prompter.java:20)
at Hangman.main(Hangman.java:9)
Any ideas on what may be causing this?
7 Answers
Chris Jones
Java Web Development Techdegree Graduate 23,933 PointsHey Nick, sorry to leave you hanging, I've been busy at work.
Just doing a quick look-over, I noticed that you have this line of code in applyGuess
method (the one that takes String letters
as a parameter:
return applyGuess(letters.charAt(letters.charAt(0)));
letters
is a String, so working from the inside out of this code says that letters.charAt(0)
will give us a char. We can't then take that char and pass it into letters.charAt
again because charAt
only takes an int.
Without looking at the course you're taking, do you need two applyGuess
methods? Seems like the user will be entering a single char, so do you just need the applyGuess
method that only takes an int as a parameter? Maybe you can throw a check in somewhere else to make sure that the user only input a single char instead of creating another method to handle it? Just thoughts, but like I said I don't know the specifics of the course.
Let me know if that helps or if I'm way off on that.
Nick Fite
11,168 PointsThanks Chris! Here's the code I have so far, class by class:
Hangman class:
public class Hangman {
public static void main(String[] args) {
// Your incredible code goes here...
Game game = new Game("treehouse");
Prompter prompter = new Prompter(game);
while (game.getRemainingTries() > 0) {
prompter.displayProgress();
prompter.promptForGuess();
}
}
}
Game class:
class Game {
public static final int MAX_MISSES = 7;
private String answer;
private String hits;
private String misses;
public Game(String answer){
this.answer = answer;
hits = "";
misses = "";
}
private char normalizeGuess(char letter) {
if(! Character.isLetter(letter)){
throw new IllegalArgumentException("A letter is required");
}
letter = Character.toLowerCase(letter);
if(misses.indexOf(letter) != -1 || hits.indexOf(letter) != -1){
throw new IllegalArgumentException(letter + " has already been guessed");
}
return letter;
}
public boolean applyGuess(char letter) {
letter = normalizeGuess(letter);
boolean isHit = answer.indexOf(letter) != -1;
if(isHit) {
hits += letter;
} else {
misses += letter;
}
return isHit;
}
public boolean applyGuess(String letters){
if (letters.length() == 0){
throw new IllegalArgumentException("No letter found");
}
return applyGuess(letters.charAt(letters.charAt(0)));
}
public int getRemainingTries(){
return MAX_MISSES - misses.length();
}
public String getCurrentProgress() {
String progress = "";
for (char letter : answer.toCharArray()) {
char display = '-';
if(hits.indexOf(letter) != -1) {
display = letter;
}
progress += display;
}
return progress;
}
}
Prompter class:
import java.util.Scanner;
class Prompter {
private Game game;
public Prompter(Game game){
this.game = game;
}
public boolean promptForGuess(){
Scanner scanner = new Scanner(System.in);
boolean isHit = false;
boolean isAcceptable = false;
do {
System.out.print("Enter a letter: ");
String guessInput = scanner.nextLine();
try {
isHit = game.applyGuess(guessInput);
isAcceptable = true;
} catch(IllegalArgumentException iae) {
System.out.printf("%s. Please try again. %n", iae.getMessage());
}
} while(! isAcceptable);
return isHit;
}
public void displayProgress() {
System.out.printf("You have %d tries left to solve: %s%n",
game.getRemainingTries(),
game.getCurrentProgress());
}
}
Chris Jones
Java Web Development Techdegree Graduate 23,933 PointsThanks, Nick. It's a little hard to read like that, but can you tell me what the code is on line 9 of the main method in the Hangman class? Looks like that's where the exception starts.
You can reference the Markdown Cheatsheet to edit your code above so it's easier to read when you post it. You basically just need to input ``` (button below the Esc button on Windows computer) before and after all of your code.
J.D. Sandifer
18,813 PointsNick, I edited your question with the markdown Chris suggested so it was more readable.
Nick Fite
11,168 Pointsprompter.promptForGuess();
is line 9 on the hangman class.
J.D. Sandifer
18,813 PointsNick, I fixed the markdown on this one for you, too.
Nick Fite
11,168 PointsAnd the promptForGuess method in Prompter:
public boolean promptForGuess(){
Scanner scanner = new Scanner(System.in);
boolean isHit = false;
boolean isAcceptable = false;
do {
System.out.print("Enter a letter: ");
String guessInput = scanner.nextLine();
try {
isHit = game.applyGuess(guessInput);
isAcceptable = true;
} catch(IllegalArgumentException iae) {
System.out.printf("%s. Please try again. %n", iae.getMessage());
}
} while(! isAcceptable);
return isHit;
}
Nick Fite
11,168 PointsJD Thank you for the edits you did to make the code more readable!
Nick Fite
11,168 PointsHey guys been a couple days since I posted this question, any ideas on what may be wrong with my code?
Nick Fite
11,168 PointsHey Chris no worries thank you for taking the time to answer! To answer your question, yes there are two applyGuess methods, one that takes a string, and one that takes a char. Thank you for drawing attention to this line: this is exactly what needed to be changed. Instead of return applyGuess(letters.charAt(letters.charAt(0))); I needed:
'''java return applyGuess(letters.charAt(0)); '''
Pretty awesome what a second set of eyes can do! Appreciate you and all the moderators at Treehouse for what you provide!
Chris Jones
Java Web Development Techdegree Graduate 23,933 PointsI'm glad I could help, Nick! Yes, a second pair of eyes has saved me before, too! Hope the rest of the course goes well!
Chris Jones
Java Web Development Techdegree Graduate 23,933 PointsChris Jones
Java Web Development Techdegree Graduate 23,933 PointsHi Nick, I'm happy to help. Can you post your code you've written?