1

I'm not sure what I'm doing wrong, the assignment is to create a code that converts a temperature from C to F or from F to C until the user decides they are finished, I'm also supposed to print an error message if an invalid character appears and have the user correct it without asking for the numeric portion again.

The program seems to run fine until I enter a value other than 'c' 'C' 'f' or 'F'. At which point I still get the desired output but than I get an error here is my code.

import java.util.Scanner;

public class ProjectThree 
{
    public static void main(String[] args)
    {
        Scanner keyboard = new Scanner(System.in);
        System.out.println("Please enter a temperature to be converted followed"
            + "\nby a C or c for Celsius or an F or f for Fahrenheit. If "
            + "\nfinished converting temperatures enter done.");
        String userInput, intString;
        userInput = keyboard.nextLine();

        while (!(userInput.equalsIgnoreCase("done")))
        {
            int length, temp, degreesC, degreesF;
            length = userInput.length();
            intString = userInput.substring(0,length - 1);
            temp = Integer.parseInt(intString);
            char scale = userInput.charAt(length - 1);

            while (!((scale == 'c') || (scale == 'C') || (scale =='f') || 
                (scale == 'F')))
            {
                System.out.println("Error: Invalid temperature unit. Enter a C or c"
                    + " for Celsius or an F or f for Fahrenheit.");
                String errorInput = keyboard.next();
                scale = errorInput.charAt(0);
                userInput = intString + errorInput;
            }
            switch (scale)
            {
                case 'C':
                case 'c':
                    degreesF = (9 * (temp / 5) + 32);
                    System.out.println(userInput + " is equal to " + degreesF 
                        + "F");
                    break;
                case 'F':
                case 'f':
                    degreesC = (5 * (temp - 32)) / 9;
                    System.out.println(userInput + " is equal to " + degreesC 
                        + "C");
                    break;
            }
            System.out.println("\nPlease enter a temperature to be converted followed"
                + "\nby a C or c for Celsius or an F or f for Fahrenheit. If "
                + "\nfinished converting temperatures enter done.");
            userInput = keyboard.nextLine();
        }
    }
}

and the error is

Please enter a temperture to be converted followed
Exception in thread "main" java.lang.StringIndexOutOfBoundsException: String index out of range: -1
by a C or c for Celsius or an F or f for Farenheit. If 
finished converting tempertures enter done.
    at java.lang.String.substring(String.java:1955)
    at ChapterFour.ProjectThree.main(ProjectThree.java:33)
Java Result: 1
BUILD SUCCESSFUL (total time: 5 seconds)
  • You should put the code in a try catch statement – Mine Rockers Nov 12 '16 at 07:25
  • Which is the input that generates this exception? – ROMANIA_engineer Nov 12 '16 at 07:26
  • Use a debugger and you will find out why you get this exception – Jens Nov 12 '16 at 07:30
  • Focus on this line: `intString = userInput.substring(0, length - 1);` and on this line `char scale = userInput.charAt(length - 1);`. You need to check the `length` value before calling those methods. – ROMANIA_engineer Nov 12 '16 at 07:37
  • I was getting the error by entering 100d it would then bring up the Error:Invalid temp box and a request to correct the temp unit which I do and then I get the desired result but the error pops up. Shouldn't none of that code run until I enter a new input? – OnlinePseudonym Nov 12 '16 at 07:52
  • I've been trying to play with the debugger in NetBeans, I'm very new to programming, about 1 week in and haven't had much use for it yet. – OnlinePseudonym Nov 12 '16 at 07:54
  • ahhhh okay, got it. I couldn't figure out why my input was being reset I changed String errorInput = keyboard.next(); to String errorInput = keyboard.nextLine(); and we are back in business! Thanks ROMANIA – OnlinePseudonym Nov 12 '16 at 08:04

2 Answers2

0

IN general, there's a lot of things that "could" go wrong on bad input, because you don't have any error checking. Here are a few things I noticed...

1) As I think someone else mentioned, you're not checking the length of any of your inputs before acting on them. If someone hits enter without anything else you will likely get an exception. Same if they enter invalid input.

2) The switch statement is missing a default clause. You should add something that prints "something went wrong please try again" just so you know it occurred.

3) I see your using keyboard.nextLine() initially and keyboard.next() when you ask only for the character. If you enter a return after the character, then the newline may be getting picked up by the following nextLine(), which causes an error to be printed as mentioned in 1 above. While Googling the behavior of next() to confirm this, I came across the following (looks like someone else had similar issue):

Issues with nextLine();

Community
  • 1
  • 1
TDWebDev
  • 86
  • 5
  • I actually took the default clause out of the switch since it can only activate with appropriate cases. Good point about adding checks for lengths! I didn't considered those input errors – OnlinePseudonym Nov 12 '16 at 09:14
0

For empty string or string of length one you didn't handle anything.So it throw an exception.You need to user try catch block or do something like i do.I simply ignore length zero and one for input string.

Scanner keyboard = new Scanner(System.in);

        System.out.println("Please enter a temperature to be converted followed"
                + "\nby a C or c for Celsius or an F or f for Fahrenheit. If "
                + "\nfinished converting temperatures enter done.");

        String userInput, intString;
        userInput = keyboard.nextLine();

        while (!(userInput.equalsIgnoreCase("done"))) {
            int length, temp, degreesC, degreesF;
            length = userInput.length();
            System.out.println(length);
            if (length > 1) {
                intString = userInput.substring(0, length - 1);
                temp = Integer.parseInt(intString);
                // System.out.println("Temp = " + temp);
                char scale = userInput.charAt(length - 1);
                // System.out.println("scale" + scale);

                while (!((scale == 'c') || (scale == 'C') || (scale == 'f') || (scale == 'F'))) {
                    System.out.println("Error: Invalid temperature unit. Enter a C or c"
                            + " for Celsius or an F or f for Fahrenheit.");
                    String errorInput = keyboard.next();
                    scale = errorInput.charAt(0);
                    userInput = intString + errorInput;
                }
                switch (scale) {
                case 'C':
                case 'c':
                    degreesF = (9 * (temp / 5) + 32);
                    System.out.println(userInput + " is equal to " + degreesF + "F");
                    break;
                case 'F':
                case 'f':
                    degreesC = (5 * (temp - 32)) / 9;
                    System.out.println(userInput + " is equal to " + degreesC + "C");
                    break;
                }
            }

            System.out.println("\nPlease enter a temperature to be converted followed"
                    + "\nby a C or c for Celsius or an F or f for Fahrenheit. If "
                    + "\nfinished converting temperatures enter done.");
            userInput = keyboard.nextLine();
        }

Note thatString substring(int beginIndex, int endIndex): Returns the substring starting from the given index(beginIndex) till the specified index(endIndex). For e.g. "Chaitanya".substring(2,5) would return "ait". It throws IndexOutOfBoundsException If the beginIndex is less than zero OR beginIndex > endIndex OR endIndex is greater than the length of String.

In your case if you simply erter c or C lenght-1 become zero which is your last index.Also your first index is also zero.That's why you got IndexOutOfBoundsException.

Hope you got it.

Real73
  • 490
  • 4
  • 13