Win a copy of TDD for a Shopping Website LiveProject this week in the Testing forum!
programming forums Java Mobile Certification Databases Caching Books Engineering Micro Controllers OS Languages Paradigms IDEs Build Tools Frameworks Application Servers Open Source This Site Careers Other Pie Elite all forums
this forum made possible by our volunteer staff, including ...
Marshals:
• Campbell Ritchie
• Paul Clapham
• Ron McLeod
• Jeanne Boyarsky
• Tim Cooke
Sheriffs:
• Liutauras Vilda
• paul wheaton
• Henry Wong
Saloon Keepers:
• Tim Moores
• Tim Holloway
• Stephan van Hulst
• Carey Brown
• Frits Walraven
Bartenders:
• Piet Souris
• Himai Minh

# Generating compound interest with integers

Greenhorn
Posts: 12
• Number of slices to send:
Optional 'thank-you' note:
I am trying to change this code to use only integers to calculate the compound interest.

This is what I have so far,

And here is the output I get,

Why do I get the output after year 2? I assume it has something to do with the remainder.

I also have to format this output with the decimal point, etc.. which I think I will be ok with after I get through this part.
Thanks!

Marshal
Posts: 75642
354
• Number of slices to send:
Optional 'thank-you' note:
Are you really taking powers of 105 or similar? Then you get 100000 × 105 × 105 which is 1102500000. Now next time you multiply by 105, you get an overflow error. Meanwhile the divisor is continuing to increase, and when the divisor is larger than the dividend, your integer division gives 0.

I am not sure what to recommend. You could try using long arithmetic, but that will eventually run out of space. The best way to calculate money is with the BigDecimal class.

David Herron
Greenhorn
Posts: 12
• Number of slices to send:
Optional 'thank-you' note:
I realize these numbers are huge and I figured that was possibly the issue. I guess I am taking the problem too literally.

After the book shows this program as an example, it goes on to say that this (using double) is not the best method for achieving accurate results, then it states "you've been warned!". It never gives a solution apart from a quick reference to the existence of BigDecimal but not how to use it.

Then I am given this problem, so that how I got here!

Thanks! I will go the BigDecimal route!

Campbell Ritchie
Marshal
Posts: 75642
354
• Number of slices to send:
Optional 'thank-you' note:

java BigDecimalDemo
No command-line arguments: enter two numbers eg 1.23 45.678:
39856398.767624534 0.00625
39856398.767625 + 0.006250 = 39856398.773875
39856398.767625 - 0.006250 = 39856398.761375
39856398.767625 × 0.006250 = 249102.492298
39856398.767625 ÷ 0.006250 = 6377023802.819925
39856398.767625 % 0.006250 = 0.005125

Note the %f tag defaults to 6 decimal places.
So far, so good. You can get 1 from 0.00625 if you repeatedly multiply by 2 or 5, so the division will eventually come out exactly. But what if the division isn't exact?

java BigDecimalDemo 9.0 0.7
Exception in thread "main" java.lang.ArithmeticException: Non-terminating decimal expansion; no exact representable decimal result.
at java.math.BigDecimal.divide(BigDecimal.java:1616)
at BigDecimalDemo.ShowOperations(BigDecimalDemo.java:25)
at BigDecimalDemo.main(BigDecimalDemo.java:41)

We now need a version 2.Apart from the imports, the change is on lines 27-28. You supply a rounding mode and a precision. In this case 4 appears to mean 4 significant figures, not four places after the decimal point. If you try to find the divide() method, you find it is overloaded about 6 times to allow for that problem. Any overloading can be used, but they may give slightly different results.
Another thing is, BigDecimal is an immutable class. You will see the values of number1 and number2 do not change in the arithmetic.
Its equals() method includes the scale as well as the value, so 1.0 and 1.00 are not the same, but new BigDecimal("1.0").compareTo(new BigDecimal("1.000") will return 0, so you can use the compareTo method.
Don't use the constructor which takes a double, but use one of the other constructors. You can see if you try System.out.println(new BigDecimal(1.23)); and with "1.23", and see the differences.
Read the BigDecimal and RoundingMode and MathContext documentation.

Campbell Ritchie
Marshal
Posts: 75642
354
• Number of slices to send:
Optional 'thank-you' note:
There is a recent discussion about problems with double and BigDecimal here.

David Herron
Greenhorn
Posts: 12
• Number of slices to send:
Optional 'thank-you' note:
Thank you for this. More than thorough. I now have this code to reference. Upon further reading, I realized the assignment is not asking us to implement BigDecimal. But since this is the proper way to do things i will be going over it as well as the RoundingMode and MathContext documentation.

Thank you again!

Campbell Ritchie
Marshal
Posts: 75642
354
• Number of slices to send:
Optional 'thank-you' note:
You're welcome

Campbell Ritchie
Marshal
Posts: 75642
354
• Number of slices to send:
Optional 'thank-you' note:

Last year, I wrote: . . . the divide() method . . . is overloaded about 6 times to allow for that problem. Any overloading can be used, but they may give slightly different results. . . .

So, try this:. . . as an alternative to line 27 above. That seems to give 4 places after the decimal point.

Campbell Ritchie
Marshal
Posts: 75642
354
• Number of slices to send:
Optional 'thank-you' note:
In the first post in this thread, the image has vanished. I think it shou‍ld be a printout like thisThat is another reason for not using screenshots: text posted doesn't mysteriously vanish.

 The airline is called "Virgin"? Don't you want a plane to go all the way? This tiny ad will go all the way: Free, earth friendly heat - from the CodeRanch trailboss https://www.kickstarter.com/projects/paulwheaton/free-heat