www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - nan question

reply bobef <bobef abv_nospam.bg> writes:
Hello,

I have a little question.
This program outputs gggg on dmd 1.21. Yes, I suck at math, but is this right
(i.e. buggy) or nans must be compared another way?


===========================

import tango.io.Stdout;

void main()
{
	double a=double.nan;
	if(a==double.nan) Stdout("1\n");
	else Stdout("g\n");
	if(a is double.nan) Stdout("2\n");
	else Stdout("g\n");
	if(double.nan==double.nan) Stdout("3\n");
	else Stdout("g\n");
	if(double.nan is double.nan) Stdout("4\n");
	else Stdout("g\n");
}
Sep 25 2007
next sibling parent Regan Heath <regan netmail.co.nz> writes:
bobef wrote:
 Hello,
 
 I have a little question.
 This program outputs gggg on dmd 1.21. Yes, I suck at math, but is this right
(i.e. buggy) or nans must be compared another way?
 
 
 ===========================
 
 import tango.io.Stdout;
 
 void main()
 {
 	double a=double.nan;
 	if(a==double.nan) Stdout("1\n");
 	else Stdout("g\n");
 	if(a is double.nan) Stdout("2\n");
 	else Stdout("g\n");
 	if(double.nan==double.nan) Stdout("3\n");
 	else Stdout("g\n");
 	if(double.nan is double.nan) Stdout("4\n");
 	else Stdout("g\n");
 }
See: http://www.digitalmars.com/d/expression.html#floating_point_comparisons In particular notice that the == row contains F in the unordered column. This means (if I'm reading it correctly) that if either operand is nan == will always give false. I think you want to have a look at isnan from std.math (not sure what Tango has), eg //example phobos-ified import std.math; void main() { double a = double.nan; if (isnan(a)) writefln("1"); else writefln("g"); } Regan
Sep 25 2007
prev sibling next sibling parent reply BCS <ao pathlink.com> writes:
Reply to bobef,

 Hello,
 
 I have a little question.
 This program outputs gggg on dmd 1.21. Yes, I suck at math, but is
 this right (i.e. buggy) or nans must be compared another way?
 ===========================
 
 import tango.io.Stdout;
 
 void main()
 {
 double a=double.nan;
 if(a==double.nan) Stdout("1\n");
 else Stdout("g\n");
 if(a is double.nan) Stdout("2\n");
 else Stdout("g\n");
 if(double.nan==double.nan) Stdout("3\n");
 else Stdout("g\n");
 if(double.nan is double.nan) Stdout("4\n");
 else Stdout("g\n");
 }
if you want to check for nan without a function call uses: fpVar !<>= 0
Sep 25 2007
parent reply bobef <bobef abv_nospam.bg> writes:
BCS Wrote:


 
 if you want to check for nan without a function call uses: fpVar !<>= 0
 
 
HAHAHAHAHAHAHAHA. I am not laughing at you, thanks for the help, but something is totally wrong. Just look at this. "!<>=" it looks almost like bytecode or 1337 or something :)
Sep 25 2007
next sibling parent Nathan Reed <nathaniel.reed gmail.com> writes:
bobef wrote:
 BCS Wrote:
 
 
 if you want to check for nan without a function call uses: fpVar !<>= 0
HAHAHAHAHAHAHAHA. I am not laughing at you, thanks for the help, but something is totally wrong. Just look at this. "!<>=" it looks almost like bytecode or 1337 or something :)
Read it as "fpVar is not less than, greater than, or equal to zero." The only 'number' that satisfies all these conditions is NaN. Thanks, Nathan Reed
Sep 25 2007
prev sibling parent "Janice Caron" <caron800 googlemail.com> writes:
On 9/25/07, bobef <bobef abv_nospam.bg> wrote:
 something is totally wrong. Just look at this. "!<>="
Well consider, the imaginary number i is not less than one. It is also not greater than one. It is also not equal to one. It makes perfect sense.
Sep 25 2007
prev sibling parent reply bobef <bobef abv_nospam.bg> writes:
Janice Caron Wrote:

 On 9/25/07, bobef <bobef abv_nospam.bg> wrote:
 something is totally wrong. Just look at this. "!<>="
Well consider, the imaginary number i is not less than one. It is also not greater than one. It is also not equal to one. It makes perfect sense.
I can't imagine such number, sorry :) But let aside my imagination. I don't know what imaginary number is, so I am not commenting if it makes sense. All I'm saying it that it is nonsense that if(double.nan!=double.nan) returns false (IMHO).
Sep 25 2007
next sibling parent reply Nathan Reed <nathaniel.reed gmail.com> writes:
bobef wrote:
 Janice Caron Wrote:
 
 On 9/25/07, bobef <bobef abv_nospam.bg> wrote:
 something is totally wrong. Just look at this. "!<>="
Well consider, the imaginary number i is not less than one. It is also not greater than one. It is also not equal to one. It makes perfect sense.
I can't imagine such number, sorry :) But let aside my imagination. I don't know what imaginary number is, so I am not commenting if it makes sense. All I'm saying it that it is nonsense that if(double.nan!=double.nan) returns false (IMHO).
I'm assuming you meant to say that it makes no sense if double.nan == double.nan returns false? But if NaNs compared equal to each other, then this: sqrt(-1) == acos(2) would be true, since both return a NaN. I bet you don't really want that. Thanks, Nathan Reed
Sep 25 2007
parent reply Don Clugston <dac nospam.com.au> writes:
Nathan Reed wrote:
 bobef wrote:
 Janice Caron Wrote:

 On 9/25/07, bobef <bobef abv_nospam.bg> wrote:
 something is totally wrong. Just look at this. "!<>="
Well consider, the imaginary number i is not less than one. It is also not greater than one. It is also not equal to one. It makes perfect sense.
I can't imagine such number, sorry :) But let aside my imagination. I don't know what imaginary number is, so I am not commenting if it makes sense. All I'm saying it that it is nonsense that if(double.nan!=double.nan) returns false (IMHO).
I'm assuming you meant to say that it makes no sense if double.nan == double.nan returns false? But if NaNs compared equal to each other, then this: sqrt(-1) == acos(2) would be true, since both return a NaN. I bet you don't really want that.
Yup, that's the reasoning. Even so, I think it probably was a mistake by the IEEE standard to violate x == x; I think the problems created by this decision are worse than the ones that were solved. (Note that they could even have used NaN payloads to detect the worst kinds of errors). But it's built into the hardware everywhere, so it's Too Late Now.
Sep 25 2007
parent reply "Janice Caron" <caron800 googlemail.com> writes:
Think of NaN as meaning "I don't know the answer".

With that understanding, when you compare two NaNs with ==, you are
asking "Is one thing I don't know the answer to equal to another thing
I don't know the answer to". The absolutely correct answer should
really be "I don't know, but probably not", but since that can't be
expressed in a bool, we go with the second best answer: no.
Sep 26 2007
parent Don Clugston <dac nospam.com.au> writes:
Janice Caron wrote:
 Think of NaN as meaning "I don't know the answer".
 
 With that understanding, when you compare two NaNs with ==, you are
 asking "Is one thing I don't know the answer to equal to another thing
 I don't know the answer to". The absolutely correct answer should
 really be "I don't know, but probably not", but since that can't be
 expressed in a bool, we go with the second best answer: no.
Yes, we're forcing 3 states (yes, no, maybe) into 2 states. IMHO, it would have been better to retain the crucial identity x==x, rather than try to detect obscure floating-point bugs. (and introduce a different operator to mean, equal-and-not-both-NaN). I use NaNs a lot (probably more than anyone else on this ng), and have not found many cases where the IEEE behaviour is helpful.
Sep 26 2007
prev sibling next sibling parent "Steven Schveighoffer" <schveiguy yahoo.com> writes:
"bobef" <bobef abv_nospam.bg> wrote in message 
news:fdbedv$2pu2$1 digitalmars.com...
 Janice Caron Wrote:

 On 9/25/07, bobef <bobef abv_nospam.bg> wrote:
 something is totally wrong. Just look at this. "!<>="
Well consider, the imaginary number i is not less than one. It is also not greater than one. It is also not equal to one. It makes perfect sense.
I can't imagine such number, sorry :) But let aside my imagination. I don't know what imaginary number is, so I am not commenting if it makes sense. All I'm saying it that it is nonsense that if(double.nan!=double.nan) returns false (IMHO).
From what I can recall reading on this message board, the behavior is exactly described as correct in the IEEE standard. Therefore, the answer is that the behavior works as designed. You need to address the rediculousness of it with the IEEE committee that designed the standard :) -Steve
Sep 25 2007
prev sibling next sibling parent BCS <ao pathlink.com> writes:
Reply to bobef,

 All I'm saying it that it is nonsense that
 if(double.nan!=double.nan) returns false (IMHO).
 
NaN is "Not A Number" and considering that we are talking about numeric equality, it is reasonable for something that isn't a NUMber to not be NUMerically equal to anything. It is sort of like comparing to nothing (not the state of nothing or a set of nothing, but the absolute omission or the entity) this assertion "x is equal to" is syntactically broken so how can it be true?
Sep 25 2007
prev sibling parent "Jarrett Billingsley" <kb3ctd2 yahoo.com> writes:
"bobef" <bobef abv_nospam.bg> wrote in message 
news:fdbedv$2pu2$1 digitalmars.com...
 I can't imagine such number, sorry :) But let aside my imagination. I 
 don't know what imaginary number is
An imaginary number is an ifloat, idouble, or ireal. ;) (Everything I know I learned from D.)
Sep 25 2007