Float is truncating?!

This is a discussion on Float is truncating?! within the C Programming forums, part of the General Programming Boards category; Alright well I'm supposed to make a program that does a few calculations and prints the results but I'm having ...

  1. #1
    Registered User
    Join Date
    Nov 2011
    Posts
    6

    Smile Float is truncating?!

    Alright well I'm supposed to make a program that does a few calculations and prints the results but I'm having a problem with the float truncating the answer.
    What I have essentialy is (Simplified version):

    float = test;
    test = 34*pow(10,9);

    but instead of test being equal to:
    34000000000

    it's equal to:
    33999998976

    Is there any way of fixing this? I tried double which solves the problem however I need to print it as a number without exponents and I can't seem to figure out how to convert double to a float.

  2. #2
    Registered User
    Join Date
    Jun 2005
    Posts
    6,198
    All floating point types have finite precision - meaning there are values that cannot be represented exactly. It is therefore always possible (even with double) to find values that will be "truncated" as you describe.

    It is a fundamental property of floating point representations so, no, you can't fix it in general. Any fix you do so 34*pow(10,9) is printed as 34000000000 rather than as 33999998976 will simply fail to behave as intended for some other set of floating point values. It's like poking a pillow: smooth a bump on one part of the pillow, and a bump appears elsewhere.

    Converting a double to a float (which can be done as float_value = (float)double_value) will not fix the problem, as converting from a double to a float loses precision. There are values a double can represent exactly that a float cannot.

    If you want to understand, there are many articles and textbooks on numerical analysis (and floating point operations) that describe this phenomenon in detail. Bear in mind that numerical analysis is a very large field. And this basic property of floating point types is the reason the field of numerical analysis exists at all.
    Right 98% of the time, and don't care about the other 3%.

  3. #3
    Registered User
    Join Date
    Nov 2011
    Posts
    6
    Well then is there a way of storing large numbers without them truncating? Int won't store such a large number, double does however I need it to print the numerical value instead of printing "3.4e^10"

  4. #4
    Registered User
    Join Date
    Jun 2005
    Posts
    6,198
    Write a little function that takes a string "3.4E+10" (the floating point form) and produces "34000000000". The logic will not be difficult.

    Just use sprintf() to produce the first string, and then output the result of your function using fprintf() (or whatever technique you prefer).
    Right 98% of the time, and don't care about the other 3%.

  5. #5
    Registered User
    Join Date
    Aug 2008
    Location
    Belgrade, Serbia
    Posts
    163
    Code:
    #include <stdlib.h>
    #include <stdio.h>
    #include <math.h>
    
    int main(void)
    {
            long double x = 34*pow(10,9);
        
            printf("%.0Lf\n", x);
        
            return EXIT_SUCCESS;
    }
    This works fine here.
    Vanity of vanities, saith the Preacher, vanity of vanities; all is vanity.
    What profit hath a man of all his labour which he taketh under the sun?
    All the rivers run into the sea; yet the sea is not full; unto the place from whence the rivers come, thither they return again.
    For in much wisdom is much grief: and he that increaseth knowledge increaseth sorrow.

  6. #6
    Registered User
    Join Date
    Nov 2011
    Posts
    6
    Alright well that worked Only one more question is there a way of evaluating if the double is less than another number? Because what I have currently doesn't work. for example:
    Code:
    double test = 34*pow(10,9);
    if(test < pow(10,12))
    {
           printf("%f", test/pow(10,9));
    }
    Last edited by JohnDeon; 11-19-2011 at 06:44 PM.

  7. #7
    Registered User
    Join Date
    Aug 2008
    Location
    Belgrade, Serbia
    Posts
    163
    What do you mean it doesn't work? Is that missing bracket that should be enclosing if a typo? Otherwise, it should work.
    Vanity of vanities, saith the Preacher, vanity of vanities; all is vanity.
    What profit hath a man of all his labour which he taketh under the sun?
    All the rivers run into the sea; yet the sea is not full; unto the place from whence the rivers come, thither they return again.
    For in much wisdom is much grief: and he that increaseth knowledge increaseth sorrow.

  8. #8
    Registered User
    Join Date
    Nov 2011
    Posts
    6
    Sorry the missing bracket is actually there in the code :P Just forgot it on the forums. But it doesn't seem to be printing anything. I have a printf() before and printf() after the if statement it prints the first one but not the second one.

  9. #9
    Registered User
    Join Date
    Aug 2008
    Location
    Belgrade, Serbia
    Posts
    163
    Then it's something else wrong with your code. It works here.

    Code:
    test$ cat dftest.c
    #include <stdlib.h>
    #include <stdio.h>
    #include <math.h>
    
    int main(void)
    {
        double test = 34*pow(10,9);
        if(test < pow(10,12))
        {
               printf("%f", test/pow(10,9));
        }
    
            return EXIT_SUCCESS;
    }
    test$ gcc -O3 -Wall -s dftest.c -o test
    test$ ./test
    34.000000
    Vanity of vanities, saith the Preacher, vanity of vanities; all is vanity.
    What profit hath a man of all his labour which he taketh under the sun?
    All the rivers run into the sea; yet the sea is not full; unto the place from whence the rivers come, thither they return again.
    For in much wisdom is much grief: and he that increaseth knowledge increaseth sorrow.

  10. #10
    Registered User
    Join Date
    Jun 2005
    Posts
    6,198
    You must be doing something else wrong.

    When you post code exhibiting a problem, trying copying the actual offending code, not writing code that does what you think the offending code does. By not doing that, you appear to be posting code that does not exhibit your problem.
    Right 98% of the time, and don't care about the other 3%.

  11. #11
    Algorithm Dissector iMalc's Avatar
    Join Date
    Dec 2005
    Location
    New Zealand
    Posts
    6,293
    Quote Originally Posted by JohnDeon View Post
    But it doesn't seem to be printing anything. I have a printf() before and printf() after the if statement it prints the first one but not the second one.
    printf "debugging" is so not the way to go about seeing what your program is really doing. What you really need to do is to use a debugger to step through the program and see exactly what happens.

    Alternatively, if you use Microsoft Visual Studio then you can insert trace points to produce output containing variable values etc as the program runs. In fact you can insert and remove these at will while the program is running. Try doing that with printf "debugging"!
    My homepage
    Advice: Take only as directed - If symptoms persist, please see your debugger

    Linus Torvalds: "But it clearly is the only right way. The fact that everybody else does it some other way only means that they are wrong"

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. truncating a file to 0 length
    By rivkyfried1 in forum C Programming
    Replies: 2
    Last Post: 10-23-2010, 07:47 PM
  2. truncating front
    By jimmianlin in forum C Programming
    Replies: 2
    Last Post: 10-01-2009, 04:12 PM
  3. Rounding/truncating float to int
    By Zzaacchh in forum C++ Programming
    Replies: 4
    Last Post: 07-02-2008, 11:21 PM
  4. Truncating a char *
    By ajb268 in forum C++ Programming
    Replies: 3
    Last Post: 01-31-2005, 01:57 PM
  5. Truncating a double?
    By criticalerror in forum C++ Programming
    Replies: 13
    Last Post: 12-08-2003, 11:49 AM

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21