CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Results 1 to 5 of 5
  1. #1
    Join Date
    Nov 2007
    Posts
    9

    g++ getline and atof

    Having an issue with the following code. I read in a decimal value from a text file, use atof (or strtod, either gives the same error) to convert the read value into a floating point number. When putting the output of atof in a double, it works fine. However when putting the output of atof into a float, the decimal places get lost. Putting the result in a double, then into a float gives the same result. This only happens when using getline.

    I've tried using temp arrays to put the result of pch in, sprintfs and such to try and work around it, but whenever a value originates from the getline command, the float value always loses decimal places. I've also tried varying the precision in the printf statement, but its always the same. When I write the float result to a file via FILE.write in binary mode, the result comes out without the decimal places when I read it back in later.

    The simple solution is to not use float and use double, but there are a number of reasons I'm using float to begin with and don't want to change that.

    Side note, this code works fine on a windows machine, the error is coming from using g++ on a mac. ANy insight would be appreciated.

    Code:
            printf("Reading from File\n");
            ifstream FILE(argv[2],ios::in);
            char BU[128];
            char *pch;
            
            // skipping lines to get to the numebers
            FILE.getline(BU,512);
            FILE.getline(BU,512);
            FILE.getline(BU,512);
            FILE.getline(BU,512);
            
            pch=strtok(BU," ");
            printf("%s\n",pch);
            
            double dval=atof(pch);
            float fval=dval;
            
            printf("%f\n",dval);
            printf("%f\n",fval);
            FILE.close();
    code output
    Reading from File
    338769.0109
    338769.010900
    338769.000000

  2. #2
    Join Date
    Aug 2012
    Posts
    4

    Re: g++ getline and atof

    Quote Originally Posted by celticfutballer View Post
    Having an issue with the following code. I read in a decimal value from a text file, use atof (or strtod, either gives the same error) to convert the read value into a floating point number. When putting the output of atof in a double, it works fine. However when putting the output of atof into a float, the decimal places get lost. Putting the result in a double, then into a float gives the same result. This only happens when using getline.

    I've tried using temp arrays to put the result of pch in, sprintfs and such to try and work around it, but whenever a value originates from the getline command, the float value always loses decimal places. I've also tried varying the precision in the printf statement, but its always the same. When I write the float result to a file via FILE.write in binary mode, the result comes out without the decimal places when I read it back in later.

    The simple solution is to not use float and use double, but there are a number of reasons I'm using float to begin with and don't want to change that.

    Side note, this code works fine on a windows machine, the error is coming from using g++ on a mac. ANy insight would be appreciated.

    Code:
            printf("Reading from File\n");
            ifstream FILE(argv[2],ios::in);
            char BU[128];
            char *pch;
            
            // skipping lines to get to the numebers
            FILE.getline(BU,512);
            FILE.getline(BU,512);
            FILE.getline(BU,512);
            FILE.getline(BU,512);
            
            pch=strtok(BU," ");
            printf("%s\n",pch);
            
            double dval=atof(pch);
            float fval=dval;
            
            printf("%f\n",dval);
            printf("%f\n",fval);
            FILE.close();
    code output
    Reading from File
    338769.0109
    338769.010900
    338769.000000
    I believe that will be due to the conversion from double to float. You could try using sscanf() instead when reading in floats. http://www.cplusplus.com/reference/c...cstdio/sscanf/
    Like this:
    Code:
    sscanf(pch, "%f", &fval);

  3. #3
    Join Date
    Oct 2002
    Location
    Austria
    Posts
    1,284

    Re: g++ getline and atof

    a 4 byte float ( single precision ) has only about 7 significant decimal digits.
    so you can only expect a float and a double to be same for 7 digits.
    if you need more precicion you have to use double.
    --> the effect that you see has nothing to do with the way you read the floating point value.
    Kurt

  4. #4
    Join Date
    Nov 2007
    Posts
    9

    Re: g++ getline and atof

    Quote Originally Posted by ZuK View Post
    a 4 byte float ( single precision ) has only about 7 significant decimal digits.
    so you can only expect a float and a double to be same for 7 digits.
    if you need more precicion you have to use double.
    --> the effect that you see has nothing to do with the way you read the floating point value.
    Kurt
    Sounds like I need to refresh myself on float. I understand it has limited precision, but it my head that always dealt with decimal places, not decimal numbers (gotta think in significant digits and eliminate the 'decimal' from my thinking). Thinking about it, you're answer explains everything (THANKS!).

    Previously, I was working with numbers on the order of 1 or maybe 10 point something, leaving enough precision after the decimal point for my purposes. However, some changes in the data forced much larger numbers and file sizes so I moved from my windows laptop with 3 gigs ram to a mac cluster with 20 gigs. I assumed it had something to do with gnu vs visual studio, but forgot about the actual change in the values. you're right, the reading in had nothing to do with it, its just that the numbers got to big for float to handle at the accuracy I wanted. When I tested it without reading a value, I used numbers on the order of 1.23123 and 13.03123. Bullocks.

    thanks for the replies, helps a lot.

  5. #5
    Join Date
    Jul 2002
    Location
    Portsmouth. United Kingdom
    Posts
    2,727

    Re: g++ getline and atof

    You're using a curious mixture of C++ (iosteams) and C (printf, scanf).

    Second, from the API of getline
    "Characters are extracted until either (n - 1) characters have been extracted..."

    Your array BU has been allocated 128 characters, but your call to getline is asking to extract a maximum of 512!
    Can you see the problem?

    You may find it easier if you were to use the global function std::getline.

    As for converting between strings and numbers, in C++ we would normally use streams for this too.

    e.g.

    Code:
    std::string text = "1.23";
    
    std::istringstream iss;
    iss.str(text);
    
    float f;
    iss >> f;
    "It doesn't matter how beautiful your theory is, it doesn't matter how smart you are. If it doesn't agree with experiment, it's wrong."
    Richard P. Feynman

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  





Click Here to Expand Forum to Full Width

Featured