Not all numbers can be represented with floating point. That's obvious since (for example) there are only 264 possible 64-bit values (less actual values since the encoding calls for things like NaNs and infinities) but an infinite number of floats.
See this answer for further explanation.
So a number like 129.95
may _actually be something like 129.949999999923234
and, when you work out intval(val * 100)
, you end up with 12994
.
One solution is to round the number instead of truncating and most languages will give you numerous ways to do that. Alternatively, you can emulate it with:
intval(val * 100 + 0.5);
Alternatively, you can avoid the problems of IEEE754 floats by not using them. Integer types are probably big enough nowadays that you can just store integral cents directly, where these sorts of errors do not occur (there may be other errors depending on the complexities of your calculations but they'll almost certainly be less than those involved in floating point).
And, if you need the larger range, you may have to opt for a BigInteger-type package.