Please help me to detect the error | Sololearn: Learn to code for FREE!
New course! Every coder should learn Generative AI!
Try a free lesson
+ 2

Please help me to detect the error

This code works fine for all decimals except 0.(3). I wasted my 1 hr but unable to figure out where I went wrong and why numberformatexception is coming for this particular input, but didn't got any solution. LukArToDo help me to find the mistake. https://code.sololearn.com/cV86SWCV8ySp/?ref=app

4th Apr 2018, 3:47 AM
Mr.Curious
Mr.Curious - avatar
20 Answers
+ 16
Buddy, put after line 42 and before line 43: r = Double.parseDouble(String.format("%."+(a[0].length()+a[1].length())+"f", r));
4th Apr 2018, 6:08 AM
LukArToDo
LukArToDo - avatar
+ 15
I even think it would be enough to put a[1] .length() as number of decimal places in String.format() expression, but with (a[0].length()+a[1].length()) we will get better precision. So, you can test solution with : r = Double.parseDouble(String.format("%."+ a[1].length()+"f", r));
4th Apr 2018, 7:09 AM
LukArToDo
LukArToDo - avatar
+ 15
RAHUL JAISWAL You're welcome 😉
4th Apr 2018, 10:40 AM
LukArToDo
LukArToDo - avatar
+ 13
Double precision gives a precision of up to 15 decimal places, and it is out the int range (number with 15 digits). The enigma is in which cases a double precision gives an "unusual" result. For example: 5.6 + 5.8 = 11.399999999999999 or 100.266-100.0=0.26600000000000534  or in your case : 0.33 *10 = 3.3000000000003 etc... Therefore, we will format the obtained number "r" into the number with the desired decimal places using String.format() In short, the String.format("%."+(a[0].length()+a[1].length())+"f", r)  syntax tells Java to return your variable (r) with (a[0].length()+a[1].length()) decimal places (which is a length of our input) in decimal representation of a floating-point number (f) from the start of the format specifier (%). So, if your input is 0.(3) -> length/or number of decimal places in String.format() expression is 5 So, if r=3.000000000004 above String.format() will return String "3.00000" After Double.parseDouble("3.00000") you will get r=3.0
4th Apr 2018, 7:03 AM
LukArToDo
LukArToDo - avatar
+ 6
Line 45 parseInt is what is crashing because the string overflows an integer number. Your double math on line 42 ends up with a tiny precision error getting the .0000000000000004
4th Apr 2018, 4:46 AM
John Wells
John Wells - avatar
+ 5
It also does it for 0.(6) 0.(9) doesn't result in an error, but also doesn't result in the correct answer. Edit, I guess it's about as close as you can get to correct though. 😉
4th Apr 2018, 5:04 AM
ChaoticDawg
ChaoticDawg - avatar
+ 5
Yes, that's true. lol, I didn't really look into what your program was doing yet at that point. I hadn't even seen that it was an epsilon issue yet. Just saw the error and that it was beyond the limits of an int. long day = tired. lol
4th Apr 2018, 5:12 AM
ChaoticDawg
ChaoticDawg - avatar
+ 4
The error is originating from this part of your call to your lowest method; Integer.parseInt(a[0]+a[1]) In the event that you enter 0.(3) as your input a[0] is "3" and a[1] is "0000000000000004". The 2 Strings are concatenated to create "30000000000000004". When this String is parsed for an int it results in an error. The max size for an int value in Java is 2147483647. You may want to try using a long type instead, but your loop in the lowest method will most likely time out in the playground.
4th Apr 2018, 4:30 AM
ChaoticDawg
ChaoticDawg - avatar
+ 4
It seems a simple fix for the issue would be to programmatically change a repeating number that begins immediately after the decimal I.E. 0.(3) to something like 0.3(3) as this seems to work fine.
4th Apr 2018, 4:55 AM
ChaoticDawg
ChaoticDawg - avatar
+ 4
It happens for 0.(6) also.
4th Apr 2018, 5:04 AM
John Wells
John Wells - avatar
+ 4
Probably not the best solution, but this seems to work. At least for 0.(3) and 0.(6). Otherwise, you may try doing some epsilon comparison checking. int lowest_a = 0; try { lowest_a = Integer.parseInt(a[0]+a[1]); } catch (NumberFormatException e) { a[1] = "0"; lowest_a = Integer.parseInt(a[0]+a[1]); } lowest (lowest_a ,(k-1)*(int)Math.pow(10,a[1].length()));
4th Apr 2018, 5:53 AM
ChaoticDawg
ChaoticDawg - avatar
+ 3
ChaoticDawg Thanks frnd it works
4th Apr 2018, 6:41 AM
Mr.Curious
Mr.Curious - avatar
+ 2
It can be due to floating point precision error ,but why it is working fine with 0.(2) , 0.(7) , etc
4th Apr 2018, 4:21 AM
Mr.Curious
Mr.Curious - avatar
+ 2
ChaoticDawg Yes I know that , but I want to know why this precision error comes only in case of 0.(3)
4th Apr 2018, 4:57 AM
Mr.Curious
Mr.Curious - avatar
+ 2
ChaoticDawg But even if I use long , it will not work as the actual value will change , giving incorrect outputs.
4th Apr 2018, 5:05 AM
Mr.Curious
Mr.Curious - avatar
+ 2
LukArToDo Thanks , it is best method , can you explain it.
4th Apr 2018, 6:42 AM
Mr.Curious
Mr.Curious - avatar
+ 2
LukArToDo Thanks alot for the explanation
4th Apr 2018, 10:34 AM
Mr.Curious
Mr.Curious - avatar
+ 1
Your code is poorly written. Bad variable names, no comments, not splitting up code into functions with good function names. You would find bugs far easier, if you did those things. I've started adding decent variable names, and it already makes more sense: https://code.sololearn.com/ch0TJXj6N2jD/?ref=app
4th Apr 2018, 4:37 AM
Emma
+ 1
John Wells Yes that is a precious error but that is coming when I am multiplying 0.33 *10 = 3.3000000000003 , further Subtracting it with 0.3, gives 3.000000000004
4th Apr 2018, 5:01 AM
Mr.Curious
Mr.Curious - avatar
+ 1
ChaoticDawg John Wells right, so what is the best way to solve this, other than converting 0.(3) to 0.3(3).
4th Apr 2018, 5:14 AM
Mr.Curious
Mr.Curious - avatar