why the code does not respond and keep runing? - java

I am writing a program that translates from Roman numerals to decimal numbers.
For some reason it does not return the value when it checks the user's input. However it already fixed,
what I'm facing right now is: The code does not respond me the number (it's keep show a blank screen after the input).
How can I fix this? Is there an issue in my code? I am just a starter so what I have learned is just basic stuff.
public static void main(String[] args) {
// Fill in the body
Scanner in= new Scanner(System.in);
String user = promptUserForNumeral(in);
while (user.length()!=0) {
int numb= convertNumeralToNumber(user);
System.out.println("The numeral "+user+ " is the decimal number "+numb);
user = promptUserForNumeral(in);
}
}
private static String promptUserForNumeral(Scanner inScanner) {
// Fill in the body
System.out.println("Enter a roman numeral (Q to quit): ");
String i = inScanner.nextLine();
while (i.length()<=0) {
System.out.println("ERROR! You must enter a non-empty line!");
System.out.println("Enter a roman numeral (Q to quit): ");
i = inScanner.nextLine();
}
if ( i.equalsIgnoreCase("q")) {
System.out.println("Goodbye!");
System.exit(0);
}
return i;
}
private static int convertNumeralToNumber(String numeral) {
// Fill in the body
int numb = 0;
int n=0;
int ch=0;
while (n<numeral.length()) {
char l= numeral.charAt(n);
numb=convertCharacterToNumber(l);
if (numb<0) {
System.out.println("Cannot be define");
n++;
}
else if (n==numeral.length()) {
ch+=numb;
}
else {
int nnumb=convertCharacterToNumber(numeral.charAt(n));
if (nnumb>numb) {
ch+=nnumb-numb;
n++;
}
else {
ch+=numb;
}
}
}
if (ch>3999) {
System.out.println("Input number must be less than 3999");
numb=ch;
}
return numb;
}
private static int convertCharacterToNumber(char numeral) {
// Fill in the body
int n=0;
if (numeral=='m' || numeral =='M') {
return 1000;
}
else if (numeral=='d' || numeral=='D') {
return 500;
}
else if (numeral=='c' || numeral=='C') {
return 100;
}
else if (numeral=='l' || numeral=='L') {
return 50;
}
else if (numeral=='x' || numeral=='X') {
return 10;
}
else if (numeral=='v' || numeral=='V') {
return 5;
}
else if (numeral=='i' || numeral=='I') {
return 1;
}
else {
return -1;
}
}
}

public class stringTest {
public static void main(String[] args) {
// Fill in the body
Scanner in= new Scanner(System.in);
String user = promptUserForNumeral(in);
while (user.length()!=0) {
int numb= convertNumeralToNumber(user);
System.out.println("The numeral "+user+ " is the decimal number "+numb);
user = promptUserForNumeral(in);
}
}
private static String promptUserForNumeral(Scanner inScanner) {
// Fill in the body
System.out.println("Enter a roman numeral (Q to quit): ");
String i = inScanner.nextLine();
while (i.length()>=0) {
if (i.length()==0) {
System.out.println("ERROR! You must enter a non-empty line!");
System.out.println("Enter a roman numeral (Q to quit): ");
i = inScanner.nextLine();
}
else if ( i.equalsIgnoreCase("q")) {
System.out.println("Goodbye!");
System.exit(0);
}
else return i; // in your program the while is never ending, so it does not return any value.
}
return "";
}
private static int convertNumeralToNumber(String numeral) {
// Fill in the body
int preNumber = 0;
int curNumber = 0;
int n=0;
int ch=0;
while (n<numeral.length()) {
char l= numeral.charAt(n);
curNumber=convertCharacterToNumber(l);
if (curNumber<0) {
System.out.println("Cannot be define");
System.exit(0);
}
else {
// I have changed the logic to evaluated decimal Number equivalent to Roman Literal
if(preNumber < curNumber && n != 0) ch = curNumber - ch;
else ch += curNumber;
preNumber = curNumber;
}
n++;
}
return ch;
}
private static int convertCharacterToNumber(char numeral) {
// Fill in the body
if (numeral=='m' || numeral =='M') {
return 1000;
}
else if (numeral=='d' || numeral=='D') {
return 500;
}
else if (numeral=='c' || numeral=='C') {
return 100;
}
else if (numeral=='l' || numeral=='L') {
return 50;
}
else if (numeral=='x' || numeral=='X') {
return 10;
}
else if (numeral=='v' || numeral=='V') {
return 5;
}
else if (numeral=='i' || numeral=='I') {
return 1;
}
else {
return -1;
}
}
}
You can probably look into promptUserForNumeral method, I think it is not necessary. You can include that in the main while loop to look for user errors.

Check this
while (i.length()>=0) {
if (i.length()==0) {
System.out.println("ERROR! You must enter a non-empty line!");
System.out.println("Enter a roman numeral (Q to quit): ");
i = inScanner.nextLine();
}
else if ( i.equalsIgnoreCase("q")) {
System.out.println("Goodbye!");
System.exit(0);
}
}
return i;
This won't quit or return anything while i.length() > 0. That return is dead code if user didn't enterq.
Solution: Specify a else with break; then it will work.
else
break;

I would rewrite your while loop :
while (i.length()<=0) {
System.out.println("ERROR! You must enter a non-empty line!");
System.out.println("Enter a roman numeral (Q to quit): ");
i = inScanner.nextLine();
}
if ( i.equalsIgnoreCase("q")) {
System.out.println("Goodbye!");
System.exit(0);
}
return i;

You have lots of redundant conditions. The problem lies within this loop:
while (i.length() >= 0) {
if (i.length() == 0) {
System.out.println("ERROR! You must enter a non-empty line!");
System.out.println("Enter a roman numeral (Q to quit): ");
i = inScanner.nextLine();
} else if (i.equalsIgnoreCase("q")) {
System.out.println("Goodbye!");
System.exit(0);
}
}
Take any value for i like "V".
It's length is greater than zero, hence it enters the loop.
It's length is again not zero in the first if condition, hence it proceeds to the elseIf
Since the value isn't a "q", the else part doesn't execute either.
So it goes back to the loop's start & again checks the condition if length is greater than zero.
So, you have an infinite loop. Work through your logic again & remove any unnecessary conditions. You can also use the break; statement to terminate the loop.

Related

Exception in thread "main" java.lang.NumberFormatException: For input string: "/3"

Below are the code. To fix the error, I simply rewrote the code in getFraction() method to den = Integer.parseInt(fracValue.substring(fracValue.indexOf("/")+1, fracValue.length())) , by adding +1. I have never seen or learn this during my courses and I just encounter this while doing project. I want to understand what the code did in num = Integer.parseInt(fracValue.substring(0, fracValue.indexOf("/"))) and den = Integer.parseInt(fracValue.substring(fracValue.indexOf("/"), fracValue.length())), we are converting the numerator to int and the num is all the values before the / and the den is all the values after the /. Am I right ? My second question is that why do we need to add +1 after the indexOf("/") ? Is it so we are taking the values after the /?
import java.util.Scanner;
public class FractionCalculator {
public static Scanner input = new Scanner(System.in);
public static void main(String[] args) {
intro();
while (true) {
String operation = getOperation();
Fraction frac1 = getFraction();
Fraction frac2 = getFraction();
Fraction result = new Fraction(1,1);
String result2 = "";
if (operation.equals("=")) {
System.out.println(frac1+" "+operation+" "+frac2+" is "+frac1.equals(frac2));
} else {
if (operation.equals("+")) {
result=frac1.add(frac2);
} else if (operation.equals("-")) {
result=frac1.subtract(frac2);
} else if (operation.equals("/")) {
if(frac2.getNumerator()==0) {
result2="Undefined";
} else {
result=frac1.divide(frac2);
}
} else if (operation.equals("*")) {
if(frac2.getNumerator()==0) {
result2 = "Undefined";
} else {
result=frac1.multiply(frac2);
}
}
//print results
} if (result2!="") {// division and multiplication by zero is undefined
System.out.println(frac1+" "+operation+" "+"0"+" = "+result2);
} else if (result.getNumerator()%result.getDenominator() == 0) {
System.out.println(frac1+" "+operation+" "+frac2+" = "+(result.getNumerator()/ result.getDenominator()));
} else {
System.out.println(frac1+" "+operation+" "+frac2+" = "+result.toString());
}
}
}
public static void intro() {
System.out.println("\nThis program is a fraction calculator");
System.out.println("It will add, subtract, multiply and divide fractions until you type Q to quit.");
System.out.println("Please enter your fraction in the form a/b, where a and b are integers.");
for (int i=0; i<80; i++) {
System.out.print("-");
}
}
public static String getOperation() {
System.out.println("\nPlease enter an operation (+, -, /, *, = or \"Q\" to quit): ");
Scanner input = new Scanner(System.in);
String operation = input.nextLine();
int x = 0;
while (x == 0) {
if (operation.equals("+") || operation.equals("-") || operation.equals("/") || operation.equals("*") || operation.equals("=")) {
x++;
} else if (operation.equalsIgnoreCase("q")) {
System.exit(0);
} else {
System.out.println("Invalid input, enter valid operation (+, -, /, *, = or \"Q\" to quit)");
operation = input.nextLine();
}
}
return operation;
}
public static boolean validFraction(String input) {
boolean valid;
if (input.startsWith("-")) {
input = input.replaceFirst("-",""); // or use 'input.substring("1", input.length())';
}
if (input.contains("-") || input.charAt(input.indexOf("/")+1)==('0') || input.contains(" ")) {
valid = false;
} else if (input.contains("/")) {
input = input.replace("/", "");
}
if (input.matches("^[0-9]+$") && input.length() > 0) {
valid = true;
} else {
valid = false;
}
return valid;
}
public static Fraction getFraction() {
System.out.println("Please enter a fraction (a/b) or integer (a): ");
String fracValue = input.nextLine();
//validate input
while (!validFraction(fracValue)) {
System.out.println("Please enter a fraction (a/b) or integer (a): ");
fracValue = input.nextLine();
}
//convert to numerator, denominator
int num = 0;
int den = 0;
if (fracValue.contains("/")) {
num = Integer.parseInt(fracValue.substring(0, fracValue.indexOf("/")));
den = Integer.parseInt(fracValue.substring(fracValue.indexOf("/"), fracValue.length()));
} else {
num = Integer.parseInt(fracValue);
den = 1;
}
// return fraction
Fraction fracConv = new Fraction(num, den);
return fracConv;
}
}
substring(int start, int end) includes the character at start and excludes the character at end. Since the integer cannot be parsed with a / in it, you need to do fracValue.indexOf("/")+1 to get just the numerical part of the denominator.
Firstly you have to understand your input
if your input is String a = "6+7", it means your string length is 3, and alloted indexes are 0,1 and 2
where 0 index is '6', 1 index is '+' and 2 index is '7'
So, when you use a.substring(0, a.indexOf("+")) it means you are saying
a.indexOf("+") = 1 index
you should get a string including '0' index but not 1 index, because substring works with inclusive first param and exclusive second param.
In case of this a.substring(a.indexOf("+")+1, a.length())
you don't want to include '+' in your denominator, So you should not include 1 index, that's why you are adding (+1) with indexof.
So, by adding +1 you are saying only pick value from a.indexOf("+") +1, i.e. 2 index,
and length of string is 3, which means you will get string inclusive of 2 index, i.e 7
if your input is "6 + 7" in that case you should use 'trim()' before using Integer.parseInt.

How do I make my code loop back to the beginning in Java?

I've read that I would need to put "continue" after an "if" statement, but every I tried this with my if statement and it states that "continue cannot be used outside of a loop."
Set it in the loop. EX:
public static void main(String[] args) {
Scanner input = new Scanner(System.in);
while (true){
System.out.print("Enter a password: The password must have at least eight characters, only letters and digits, and at least two digits. ");
String s = input.nextLine();
if (thepassword(s)) {
System.out.println("Valid Password");
break;
} else {
System.out.println("Invalid Password");
}
}
}
See more : Java Break and Continute
Use an outer infinite loop with a lable, then break the loop using break loop_lable. Check until a valid input is made.
import java.util.*;
public class Main {
public static void main(String[] args) {
Scanner input = new Scanner(System.in);
System.out.print("Enter a password: The password must have at least eight characters, only letters and digits, and at least two digits. ");
loop:for(;;)
{
String s = input.nextLine();
if (thepassword(s))
{
System.out.println("Valid Password");
break loop;
}
else
{
System.out.println("Invalid Password");
continue loop;
}
}
input.close();
}
public static boolean thepassword(String password) {
boolean thepassword = true;
if (password.length() < 8) {
thepassword = false;
} else {
int totaldigits = 0;
for (int n = 0; n < password.length(); n++) {
if (thedigit(password.charAt(n)) || theletter(password.charAt(n))) {
if (thedigit(password.charAt(n))) {
totaldigits++;
}
} else {
thepassword = false;
break;
}
}
if (totaldigits < 2) {
thepassword = false;
}
}
return thepassword;
}
public static boolean theletter(char c) {
return ((c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z'));
}
public static boolean thedigit(char c) {
return (c >= '0' && c <= '9');
}
}

While Loop Parsing Issue

I'm trying to give the user an infinite amount of inputs until they enter q. I'm using a while statement to run the program, but when the user tries to quit I get an error because the program would try and parse q as an integer. Any ideas on how I should change the structuring of this to prevent the error from occurring?
Scanner in = new Scanner(System.in);
System.out.println("What would you like your Fibonacci number to be?(enter q to quit)");
String value = in.next();
int trueValue;
while(!value.equalsIgnoreCase("q")) {
trueValue = Integer.parseInt(value);
Fibonacci userCase = new Fibonacci(trueValue);
System.out.println(userCase.calculateFibonacci(userCase.getCaseValue()));
System.out.println("Please enter another number.");
value = in.next();
trueValue = Integer.parseInt(value);
}
If it matters, here are the methods being called within the loop.
public int calculateFibonacci(int caseValue) {
if(caseValue == 0)
return 0;
else if(caseValue == 1)
return 1;
else
return calculateFibonacci(caseValue-1) + calculateFibonacci(caseValue-2);
}
public int getCaseValue()
{
return caseValue;
}
You can remove the last
trueValue = Integer.parseInt(value);
since you are already doing that at the start of the loop.
do{ getting the user value before checking } while(checking if it's ok);
/* https://stackoverflow.com/questions/40519580/trying-to-determine-if-a-string-is-an-integer */
private boolean isInteger(String str) {
if(str == null || str.trim().isEmpty()) {
return false;
}
for (int i = 0; i < str.length(); i++) {
if(!Character.isDigit(str.charAt(i))) {
return false;
}
}
return true;
}
public static String check(Scanner in) {
String value;
do {
System.out.println("Please enter a number or q to quit.");
value = in.next();
} while(!value.equalsIgnoreCase("q") && !isInteger(value));
return value;
}
public static void main (String[] args) {
Scanner in = new Scanner(System.in);
String value = check(in);
while(!value.equalsIgnoreCase("q")) {
Fibonacci userCase = new Fibonacci(Integer.parseInt(value));
System.out.println(userCase.calculateFibonacci(userCase.getCaseValue()));
value = check(in);
}
in.close();
}

Some trouble in loop

Hi there,
I'm a newbie in java and I have a problem with this code. I'm thinking if it is a problem in loop or something..
public static void main(String[] args) {
try {
Scanner scn = new Scanner(System.in);
int z = 0;
String input;
int[] ABArray = new int[2];
while (z == 0) {
System.out.println("Input X to terminate.");
System.out.print("Input: ");
input = scn.nextLine().toLowerCase();
for (int i = 0; i < input.length(); i++) {
char AB = input.charAt(i);
ABArray[AB - 'a']++;
}
if (ABArray[0] == 0 || ABArray[1] == 0) {
System.out.println("Not Equal");
System.out.println("");
} else if (ABArray[0] == ABArray[1]) {
System.out.println("Equal");
System.out.println("");
} else if (ABArray[0] != ABArray[1]) {
System.out.println("Not Equal");
if (ABArray[0] > ABArray[1]) {
System.out.println("The number of A is greater than B.");
} else if (ABArray[0] < ABArray[1]) {
System.out.println("The number of B is greater than A.");
}
System.out.println("");
}
}
} catch (ArrayIndexOutOfBoundsException X) { } //Terminates the program
}
The problem is this
I/O
Input:
ABABAB
Output:
Equal
Input:
AABBB
Output:
Not Equal
The number of B is greater than A.
Input:
AABB //It is equal.
Output:
Not Equal //It says not.
The number of B is greater than A.
As you see, the problem is when I input equal A and B at the first, it says equal, when I input not equal A and B but at the third when I input equal A and B it says not equal.
Problem solved.
Thanks for the help.
You have to set all the values in ABArray to zero every time you start to work inside the while loop. Right now on the third time you start the while loop (with AABB input) you still keep the values which were left from the previous run of the loop - 5 in the 0-indexed element of an array and 6 in the 1-indexed element of an array, thus the program gives you the wrong output.
How about you simply read in the input into a string, then loop through it, counting the number of occurrences of each character you are interested in (here 'a' and 'b'), checking whether their counts are equal? So this works for example:
public static void main(String[] args) {
try {
Scanner scanner = new Scanner(System.in);
String input;
while (true) {
System.out.println("Input X to terminate.");
System.out.print("Input: ");
input = scanner.nextLine().toLowerCase();
if (input.equals("X")) {
break;
} else {
int countA = 0;
int countB = 0;
for (int i = 0; i < input.length(); i++) {
if (input.charAt(i) == 'a') {
countA++;
} else if (input.charAt(i) == 'b') {
countB++;
}
}
if (countA == countB) {
System.out.println("Equal!");
} else {
System.out.println("Not equal!");
}
}
}
} catch (ArrayIndexOutOfBoundsException e) // Terminates the program
{
}
}
You can use this code:
public static void main( String[] args )
{
try
{
Scanner scn = new Scanner(System.in);
int z=0;
String input;
int[] ABArray = null;
while(z==0)
{
ABArray = new int[2];
System.out.println("Input X to terminate.");
System.out.print("Input: ");
input=scn.nextLine().toLowerCase();
for ( int i = 0; i < input.length(); i++ )
{
char AB=input.charAt(i);
ABArray[AB-'a']++;
}
if(ABArray[0]==0||ABArray[1]==0)
{
System.out.println("Not Equal");
System.out.println("");
}
else if(ABArray[0]==ABArray[1])
{
System.out.println("Equal");
System.out.println("");
}
else if(ABArray[0]!=ABArray[1])
{
System.out.println("Not Equal");
if(ABArray[0]>ABArray[1])
{
System.out.println("The number of A is greater than B.");
}
else if(ABArray[0]<ABArray[1])
{
System.out.println("The number of B is greater than A.");
}
System.out.println("");
}
}
}
catch(ArrayIndexOutOfBoundsException X) //Terminates the program
{
X.printStackTrace();
}
}

Boolean bug (FibonacciNumbers)

First of all I am not asking anyone to do anything just need a little help to fix this bug with boolean. I put false but the program stops. I got two parts to the program.
First part where i did the calculations:
class FibonacciNumbers {
FibonacciNumbers() {} //default constructor
public int fOf(int n) {
if (n == 0) //the base case
{
return 0;
} else if (n == 1) {
return 1;
} else {
return fOf(n - 1) + fOf(n - 2);
}
}
}
Second where the main method is:
import java.util.*;
public class FibonacciNumbersTesters {
public static void main(String[] args) {
FibonacciNumbers fNumbers = new FibonacciNumbers(); //creates new object
Scanner in = new Scanner(System.in);
String again;
String test;
boolean IsRepeat = true;
boolean isQuit;
try {
isQuit = false;
while (!isQuit) {
System.out.print("Enter the number you want to convert to Fibanocci('q' to quit): ");
int n = in.nextInt();
System.out.print("The Fibanocci number for " + n + " is: ");
n = fNumbers.fOf(n);
System.out.println(n);
System.out.print("Do you want to run again? (Y or N): ");
again = in.next();
if (again.equalsIgnoreCase("N")) {
System.out.println("Thank you! Please terminate the program by entering 'Q' or 'q' OR you can cotinue by entering anything else: ");
String toQuit = in.next();
if ((toQuit.charAt(0) == 'q') || (toQuit.charAt(0) == 'Q')) {
System.out.println("Good-bye!");
isQuit = true;
}
} else {
IsRepeat = true;
}
}
} catch (InputMismatchException ex) {
test = in.nextLine();
if ((test.charAt(0) == 'q') || (test.charAt(0) == 'Q')) {
System.out.println("Good-bye!");
isQuit = true;
} else {
System.out.println("Invalid input!");
System.out.println("Try again! ");
isQuit = false;
}
}
}
}
This part where i put isQuit = false; at the end it just stops. I want it to continue.
Try putting your try catch statement inside of your while loop.

Categories