Why does my string to float-conversion not get all decimals with istringstream?

I am reading a delimiter-separated file line by line and splitting the input by the delimiter '|' thats used in the file. While reading the line I need to convert a input like "1.9" or "2.38" to a float, but I cant seem to make it work. All i get is the first number like "1" or "2.".

What's wrong with my code? My Struct person looks like this:

struct person {
    string firstname;
    string lastname;
    string signature;
    float length;

    string getFullName() {
        return firstname + " " + lastname;
    }
};

My Method:

vector<person> LoadFromFile(string filename) {
    string line;
    vector<person> listToAddTo;
    person newPerson;

    ifstream infile(filename);
    if (!infile) {
        cerr << "Error opening file." << endl;
        //Error
    }

    while (getline(infile, line)) {
        string field;
        vector<string> fields;
        istringstream iss_line(line);
        while (getline(iss_line, field, DELIM)) {
            fields.push_back(field);
        }

        newPerson.firstname = fields[0];
        newPerson.lastname = fields[1];
        newPerson.length = strtof((fields[2]).c_str(),0);
        newPerson.signature = fields[3];

        listToAddTo.push_back(newPerson);
   }
return listToAddTo;
}

And the textfile:

morre|bo|1.8|morbox1|
mo|her|1.8|moxher1|
mo|herm|1.9|moxher2|

I tried isolating the problem by writing the input to a string, which displays the results just fine.
So the problem seems to be with the conversion from string to float:

newPerson.length = strtof((fields[2]).c_str(),0);

1 answer

  • answered 2018-01-16 21:04 Bob__

    Looking at the documentation about std::strtof at cpp.reference we can find that

    ... it takes as many characters as possible to form a valid floating-point representation and converts them to a floating-point value...

    Where "a valid floating-point representation" can be a

    ... nonempty sequence of decimal digits optionally containing decimal-point character (as determined by the current C locale) (defines significand)

    Apparently, in OP's locale the decimal-point character was not a ., like in the file they were trying to read, so the numbers were misinterpreted.

    It's worth noting that, since C++11, we can convert a std::string into a number directly, using std::stof instead.