On Monday, 24 March 2014 at 03:55:41 UTC, bearophile wrote:
This kind of code sometimes is wrong, because you forget to
cast x to double before the division and you lose precision
(but here the compiler knows that the result of the division
will go inside a double):
void main() {
int x = 15;
double y = x / 10;
}
The cause is that unfortunately in D the integer division uses
the same operator as the FP division. In Python there is the /
and // operators. In OcaML there are the / and /., in Delphi
there are the / and div operators, in Ada the two operands need
to be of the same type.
Seasoned C/C++/D programmers watch for the types every time
they perform a division, to avoid that trap. But less
experienced programmers introduce bugs with divisions. Can D
help the programmer reduce the frequency of similar bugs? And
do we want to?
Bye,
bearophile
It is indeed a common floating-point bug.
I came up with a solution for this a couple of years ago, never
got around to doing a pull request, but it's on the newsgroup
somewhere. It's a little extension to the range propagation
implementation. You add a boolean flag to the range, which
indicates 'a fractional part has been discarded'. This flag gets
set whenever you perform an integer division (or integer
exponentiation with a negative power), and is cleared whenever
there is a cast or a bitwise operation.
Then, disallow implicit casting from integer to floating point
whenever the fractional bit is set. Catches all these kinds of
bugs, doesn't require any changes to the language.