14

Possible Duplicate:
Checking if a double (or float) is nan in C++

I have a requirement to check if float is NaN. By going through some of the links I found the most common check.

FLOAT32 f32_test_NaN = (some_value);
if (f32_test_NaN == f32_test_NaN)
{
    //do something;
}
else
{
    // do something;
}

But this does not seem to work for me. My code is as follows:

FLOAT32 test_NaN = 0x414570A3;//some value - is this ok?

Debugging on GDB:

(gdb) p test_NaN
$1 = 1.09506982e+09

(gdb) p/x test_NaN
$2 = 0x41457080 // Hex is not same as init value - What is compiler doing?

So in my case test_NaN is equal to test_NaN.

Please let me know if any compiler setting has to be done. I am running on solaris. Or is there any other way to check the same.

Thanks in advance.

Community
  • 1
  • 1
kp11
  • 2,055
  • 6
  • 22
  • 25

4 Answers4

23

Include math.h and use int isnan(x). Don't forget to link with -lm

SiegeX
  • 135,741
  • 24
  • 144
  • 154
10

If <math.h> is not available, then do this:

if (x != x)
{
    // x is NaN
}
Oliver Charlesworth
  • 267,707
  • 33
  • 569
  • 680
  • Thanks, its the same I am doing, but probably I am not initializing correctly. Can you tell me what value I can initialize 'x' with to test for NaN? – kp11 Jan 20 '11 at 08:35
  • @kp11 Any floating point expression should do. – fuz Mar 25 '20 at 15:30
7

if (x != x)

For x = 0x7FBFFFFF (sign bit 0, a = 0, rest of bits 1)

http://en.wikipedia.org/wiki/NaN

A bit-wise example of a IEEE floating-point standard single precision (32-bit) NaN: s111 1111 1axx xxxx xxxx xxxx xxxx xxxx where s is the sign, x is the payload, and a determines the type of NaN. If a = 1, it is a quiet NaN; if a is zero and the payload is nonzero, then it is a signaling NaN

1

The problem is maybe in your initialization (at least that explains the value you see in gdb) :

FLOAT32 test_NaN = 0x414570A3;

The hex value given is considered as an integer and converted to float (with exponent and value) meaning it is stored in a different format.

If you want to force the bits inside the float, then you need to memcpy:

FLOAT32 test_NaN;
memcpy(&test_NaN, 0x414570A3, 4);
Benoit Thiery
  • 6,325
  • 4
  • 22
  • 28
  • Cool!! I knew problem was there. But memcpy crashed for me though. Hence is just did this and it worked!! UINT32 test_NaN[2] = {0xffffffff,0xfffffff7}; FLOAT32 test = *( FLOAT32* )test_NaN;(not showing pointers in comments (?!?)) – kp11 Jan 20 '11 at 09:01
  • 6
    Your code is incorrect. memcpy must copy from address. So store 0x414570A3 in an int variable first. – Calmarius Dec 23 '13 at 19:07