0

I'm comparing simple floats and doubles in C, specifically the value 8.7 for both of them. Now I assign 8.7 to each variable, when I print I get a result of 8.7000 for both values. Why has the compiler added these zeros. And the main question I wanted to ask was is there any further numbers that I'm not seeing, as in hidden after the trailing zeros. I read that I shouldn't do comparisons like this with float because of a lack of precision, but I thought with such a small value surely it can store 8.7 with a degree of accuracy needed to compare itself with another 8.7 value?

My only worry is that its actually being represented somewhere in memory as eg 8.70000003758 or something, which is throwing my comparisons off? I tried to printf with %.20f to see any further numbers that might be hiding but I think that just created numbers that were otherwise not there as the whole accuracy of the number changed to 8.6918734634834929 or something similar.

John Setter
  • 175
  • 1
  • 17
  • 1
    Possible duplicate of [How to represent FLOAT number in memory in C](http://stackoverflow.com/questions/6910115/how-to-represent-float-number-in-memory-in-c) – David Hoelzer Feb 01 '16 at 22:34
  • 1/3 is a small value. But no fixed-precision decimal representation can store it exactly. Your reasoning is completely invalid. – David Schwartz Feb 01 '16 at 22:36
  • If you really want to see the difference, try running the application inside of gdb and looking at the two variables. You will be able to see the internal representations. You will have to look up how floating point numbers are represented in the above comment. – bruceg Feb 01 '16 at 22:39

1 Answers1

3

I'm comparing simple floats and doubles in C, specifically the value 8.7 for both of them.

Bad choice, since 8.7 has no exact binary representation.

Now I assign 8.7 to each variable, when I print I get a result of 8.7000 for both values. Why has the compiler added these zeros.

It hasn't, your print routine has.

And the main question I wanted to ask was is there any further numbers that I'm not seeing, as in hidden after the trailing zeros.

Definitely, since 8.7 has no exact binary representation. (Try to write it out as the sum of integer powers of 2, you can't do it.)

I read that I shouldn't do comparisons like this with float because of a lack of precision, but I thought with such a small value surely it can store 8.7 with a degree of accuracy needed to compare itself with another 8.7 value?

You thought wrong. 1/3 is small but has no exact decimal representation with a finite number of digits. Whether a value is big or small has nothing to do with whether it can be represented exactly with a finite number of digits in a particular base.

My only worry is that its actually being represented somewhere in memory as eg 8.70000003758 or something, which is throwing my comparisons off?

Exactly, just as representing 1/3 as 0.333333333 would do.

I tried to printf with %.20f to see any further numbers that might be hiding but I think that just created numbers that were otherwise not there as the whole accuracy of the number changed to 8.6918734634834929 or something similar.

That's probably just a bug. Show us that code. Perhaps you tried to output a double and left out the l.

David Schwartz
  • 179,497
  • 17
  • 214
  • 278
  • Ok thanks for a clear answer. Is there a way to truncate any numbers after a certain decimal to do an accurate comparison for my purpose. All I want is a decimal number that can be compared float != double. But I need a roughly accurate figure, even to 1 dp is fine – John Setter Feb 01 '16 at 22:48
  • @JohnSetter please don't compare floating point numbers for equality even when they are the same type - never mind different types. See [Is floating point math broken?](http://stackoverflow.com/questions/588004/is-floating-point-math-broken) – Weather Vane Feb 01 '16 at 22:53
  • 4
    You can easily compare floating-point numbers for approximate equality. The simpleminded way is with code like `if(fabs(a - b) < 0.001)`. See the C FAQ list for a better answer: http://c-faq.com/fp/fpequal.html – Steve Summit Feb 01 '16 at 22:53