Float consistency

D

David W

Hello,

float nanometers(long pm)
{
return pm / 1000.0f;
}

void f()
{
if(nanometers(309311L) == nanometers(309311L))
{
// do something
}
}

Is there any way to force the VS .NET 2003 C++ compiler to produce a result of true for the 'if'
expression above? I get false even with the /Op switch. The original code from which I created the
example produced true on an earlier compiler (1.52c). The project is large and I don't know how many
similar problems are lurking in it and there's no easy way to look for them.

DW
 
B

Brian Muth

David W said:
Hello,

float nanometers(long pm)
{
return pm / 1000.0f;
}

void f()
{
if(nanometers(309311L) == nanometers(309311L))
{
// do something
}
}

Is there any way to force the VS .NET 2003 C++ compiler to produce a
result of true for the 'if'
expression above? I get false even with the /Op switch. The original code
from which I created the
example produced true on an earlier compiler (1.52c). The project is large
and I don't know how many
similar problems are lurking in it and there's no easy way to look for
them.

DW

The best advise is to upgrade to VS 2005 which doesn't exhibit this problem.
The VS 2003 C++ compiler is storing the intermediate float number in a dword
space in memory, but when it reloads it back into the floating point
register, there is extra garbage in the low order bits since the FP register
is much wider than the dword. VS 2005 C++ compiler gets around this by
storing the intermediate values in a qword memory space.

Having said this, this is still somewhat dangerous code to use. Checking for
equality between floating pointer numbers is frought with danger because of
implicit numerical roundoff when fractions are computed within the FP
registers and truncated to fit the register.

HTH

Brian
 
D

David W

Brian Muth said:
The best advise is to upgrade to VS 2005 which doesn't exhibit this
problem.

Quite an expensive fix, not to mention the time involved in getting a large
project rebuilt with a new compiler. No 2003 service pack that fixes it? If
there isn't there should be, given the outlay.
The VS 2003 C++ compiler is storing the intermediate float number in a dword
space in memory, but when it reloads it back into the floating point
register, there is extra garbage in the low order bits since the FP register
is much wider than the dword. VS 2005 C++ compiler gets around this by
storing the intermediate values in a qword memory space.

Having said this, this is still somewhat dangerous code to use. Checking for
equality between floating pointer numbers is frought with danger because of
implicit numerical roundoff when fractions are computed within the FP
registers and truncated to fit the register.

Yes, I'm aware of the danger, but, intuitively, you would expect identical
starting values and identical operations to produce identical results, even
in floats. In the real program the calculation is more involved, but the
inputs are longs and ints, not floats.

David
 
C

Carl Daniel [VC++ MVP]

David said:
Quite an expensive fix, not to mention the time involved in getting a
large project rebuilt with a new compiler. No 2003 service pack that
fixes it? If there isn't there should be, given the outlay.

Service pack 1 for VS2003 was recently released [1]. Have you tried it?

If it doesn't fix the problem, your only other option is to call Product
Support to see if there's a hotfix available.

[1] http://support.microsoft.com/?kbid=918007

-cd
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top