RPN is a slightly unusual four function calculator for Android. It’s designed to replace the standard built-in calculator, and features large buttons designed for easy touchscreen use.
It has three unusual features:
- It uses Reverse Polish Notation, as commonly found on HP calculators.
- It uses decimal arithmetic.
- It uses fixed point.
It does not offer scientific functions, unit conversions, base conversions, programmability, memory registers, or any other advanced functionality, because I don’t need those things when I’m away from my desk, and I wrote the program to “scratch my itch”. If you need that stuff, there are at least half a dozen scientific calculators available for free in the Android Market, including an HP48 emulator.
The calculator offers an indefinite stack size, and the stack items are preserved if you need to switch to another app.
On Android 2.x, the top left button is a shift key which swaps the keys to a secondary set. This allows me to squeeze in a few extra functions like swap, drop and reciprocal in spite of limited screen space. On Android 4.x devices, screens are bigger, so I dropped the shift key in favor of an extra row of shorter buttons.
Also, note that the keyboard’s color is different depending on your OS version — Android 2.x had light gray keys, whereas on Android 4 the app uses the standard Holo look and feel.
One key secondary function is ‘SET DP’ to set the number of decimal places displayed. Type a number then push SET DP.
The left arrow on the main keyboard deletes the last digit typed. If there was no last digit typed (i.e. the last key pressed was enter or a mathematical operation), it drops the top item from the stack.
Skip to the bottom for licensing info. Read on if you’re interested to know why I built it the way I did.
What was wrong with the existing apps?
A smart programmer doesn’t write any code unless he has to. Before firing up Eclipse, I checked the existing calculator apps to see if one of them would meet my needs.
I’m a software guy. The only times I need to carry out a complicated calculation, I already have a computer in front of me. I can open a spreadsheet, start an interactive Ruby session, or even use the HP16c that sits on my desk.
So my phone calculator just needs to be able to deal with tasks like figuring out my share of a restaurant bill, calculating the tip, or totaling the parts list for a trip to the hardware store.
The calculator that came with my phone was HTC’s Sense UI replacement for the stock Android calculator. It has the incredibly irritating “feature” that after you push = and the result is displayed, pushing a number appends the number to the result of the previous calculation, rather than starting a new calculation. The standard Android calculator lacks that misfeature, but it still isn’t RPN. (See below for why that’s important to me.)
I tried various RPN calculators from the Android Market. They all had 7 or more rows of buttons to handle all the scientific and technical functions I never use. That’s a problem because the smaller the buttons are on the touchscreen, the more fiddly and error-prone it is to use the calculator.
So, I decided I’d have to build myself a four-function RPN calculator with nice big buttons.
What’s so great about RPN? Consider one of the tasks I mentioned earlier: totaling up a parts list.
3 @ 3.99 2 @ 1.99 4 @ 6.99
With an algebraic calculator, you enter everything in one long stream: 3 x 3.99 + 2 x 1.99 + 4 * 6.99. Then you hit =, and hope that you got everything right, so that what is displayed is the correct answer. Not too painful to do in this case; but the more items on the list, the more likely you are to make a mistake, not realize until it’s too late, and have to start again from scratch.
If you’re smart, you do what I was taught to do in school: Break the calculation into pieces. You’ll write down a sub-total for each row, and then do a separate calculation to add the sub-totals together. Of course, this requires that you have paper and pen available.
Now consider how you perform the calculation in RPN. Forget about the name, the idea of RPN is very simple: you enter the numbers first, and then say what to do with them.
On RPN calculators, there’s an enter key (shown on my calculator with the right-angled arrow typically found on keyboards). In addition, the add, subtract, multiply and divide buttons also implicitly enter whatever number you were typing, before performing the appropriate operation.
Take addition, for example. To add 23 and 42, you’d type 23 enter 42 + and you’d get the answer. You type the first number, hit enter to put it on the stack of temporary numbers, type the second number, and then push the add button. The add button puts the second number on the stack of numbers and then immediately takes two numbers from the stack and adds them together. The result is put back on the stack, and displayed to you.
So, let’s now go back to the parts list example. You start with 3 enter 3.99 x, and the calculator shows you the first partial result. Then you type 2 enter 1.99 and the calculator shows you the second partial result. If both look OK–and you can see them both on screen–you hit + and add them together to form a new sub-total. Finally, you type 4 enter 6.99 x, see that you got that line right, and hit + one last time to get your final total.
Because you see all the partial results, you can catch errors more quickly. You can also zero out an incorrect partial result and re-enter that part of the calculation, without having to start the whole thing again.
At school, I used my calculator’s memory to store partial results. Casio even provided an M+ button to add a partial result to the value in memory; if the partial results needed to be multiplied or divided, though, I had to resort to paper and pen. Then I learned about RPN, and realized I was effectively doing calculations the RPN way, using the display and the memory as a 2-level stack.
Cash registers and paper roll calculators (also known as printing calculators or adding machines) often encourage RPN-like operation via += buttons. The classic HP12C RPN calculator still has a cult following amongst accountants and business professionals, precisely because RPN makes you more likely to spot errors.
Another advantage of RPN is that you never need to use brackets to change the order of calculation–for example, if you want to work out (1+2)*3 rather than 1+(2*3). That, in turn, means you don’t need to remember whether you have a bracket left open.
A final advantage to RPN might be that it doesn’t confuse people who aren’t very good at math. A recent study by Texas A&M suggests that use of algebraic calculators has resulted in a generation of students who think that ‘=’ is an operation, rather than a statement that both sides of the symbol are equal in value. Since RPN only uses symbols that represent mathematical operations to represent operations, it won’t confuse students into thinking of ‘=’ as a verb.
Once you get used to RPN, it’s annoying to use an algebraic calculator. Try it, you might like it.
Why decimal arithmetic?
Try the following simple calculation on your Android phone’s built-in calculator:
3322.72 - 3321.92 =
On Android 2.1, I get 0.79999999999. To understand why, you need to know a bit about computer history.
Far back in the mists of time, computer memory (RAM) was incredibly expensive, and computers were slow. My first computer had 1KiB of RAM, and ran at 4MHz. Because memory was so expensive, it was important to pack data into as little space as possible. This was done by storing all numbers in binary, the native format understood by digital computers. Binary numbers were also much faster to perform arithmetic on, so it was a win/win.
This way of handling numbers became a part of almost every major programming language. So, when the standard Android calculator works on your calculation, it first converts each number into binary, then performs the calculation, then converts the result back into decimal.
Unfortunately, many everyday decimal numbers don’t convert cleanly into binary. The number 0.1, for example, turns into an infinitely long binary number. When you happen to use a number that doesn’t convert cleanly, you can get an error like the one above.
Fortunately, there’s an alternative. My phone has 500,000x the memory, and runs at 150,000x the speed, of my first computer. There really isn’t any need to pack numbers into a few bytes any more. So, my calculator program uses decimal arithmetic; that is, it performs the calculations exactly like you would if you were using pen and paper. That way, you get right answer, at the expense of a little battery power.
There is one limitation you need to be aware of, though. Obviously, not all calculations are easily expressed as decimal numbers either. If you calculate 1 / 3, the result is a recurring fraction. Popular desktop calculators typically compute values to around 10 to 15 digits of accuracy–Casio usually guarantee 10 digits, TI’s BA II Plus calculates to 13 digits, and current HP RPN calculators have 15 digit accuracy. My calculator computes up to 32 digits after the decimal point, regardless of how large the number is, so it should perform more accurately than any pocket calculator you can buy in a store.
One final issue is rounding. When the value can’t be represented exactly, it can either be rounded up, or rounded down. There are various different algorithms for performing rounding. I use round half even during calculations, in order to minimize error. I then use round half up for display only, because that’s the everyday rounding method people are familiar with. (I may add a preference for round-half-even display in the future.)
Why fixed precision?
In everyday calculations, there’s a limit to how much precision you need. If you’re working in dollars and cents, you only care about seeing 2 digits after the decimal point. If you’re working in Euro, you need 4 digits. If you’re working out the amount of wood you need for a home improvement project, you probably only care about 1 or 2 digits. Simple calculators like the Android built-in calculator don’t give you any way to limit the displayed precision to a sane value; they just display as many digits as the answer seems to have, until they fill the display.
More annoying still, if you add $2.75 and $5.25 on a regular calculator, you get 8. Not 8.00, just 8. This isn’t too helpful, and is worse on a stack-based calculator where you might have 2.85 on the line above.
So, my calculator displays the exact number of decimal places you tell it to. No more, no less. As mentioned above, the calculation is always performed to outrageous precision; it’s just rounded to the number of decimal places you specify for display purposes.
The top left button, with a symbol that looks like a dot inside a square, is used to set the precision. Just type the number of digits you want, then hit that button.
That’s about all I have to say about calculators. Most of the issues above apply to spreadsheets too, and some day I’d love to have a spreadsheet that performs arithmetic correctly. (None of the popular ones do.)
My calculator is free software. I built it for myself, but I figured I might as well give it away to others who might appreciate it. If you find any bugs, please let me know.
- RPN, An introduction to Reverse Polish Notation by HP.
- RPN or DAL? compares RPN with algebraic calculator operation, and shows how RPN takes fewer keystrokes.
- The General Decimal Arithmetic web site
- Java theory and practice: Tricks and traps with floating point and decimal numbers
- Other Android calculators
GNU Public License
The code is available under the GNU Public License, version 3 or later. I would particularly like to draw your attention to the following clauses:
15. Disclaimer of Warranty.
THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM “AS IS” WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION.
16. Limitation of Liability.
IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.