Caleb
Caleb

Reputation: 3

File data read to map, but map::find() doesn't work

I need to find a key/value pair in a map, but due to how the map is populated, for some reason map::find() doesn't work.

The data it reads from can be boiled down to

Key1,a,b,c
Key2,a
Key3
Key4,a,b

With this I could print out all this data using an iterator loop, but map::find() does not work with Key3 or Key4.

Data is gathered from the file as such:

file.open("input.txt");
std::string line;
std::string key;
while(getline(file,line,','))
{
    key = line;
    getline(file,line);
    m[key]=line;
}

Which can be printed with:

for(auto it = m.begin(); it != m.end(); ++it)
{
    std::cout<<it->first<<","<<it->second<<std::endl;
}

Output:

Key1,a,b,c
Key2,a
Key3
Key4,a,b

But for whatever reason, Key3 and Key4 don't exist according to map::find().

I've tried checking error bits, manually setting the value for Key3, nothing seems to work that allows me to use map::find() for values after Key3. (map::find() returns map.end() for those values)

I'm almost certain it's because of how I gather the data, specifically because Key3 doesn't have a comma, but I have to leave it in that form.

Upvotes: 0

Views: 65

Answers (2)

Caleb
Caleb

Reputation: 3

So while this doesn't explain what the original issue was, here is the solution I found.

Gathering data from the file is now

file.open("input.txt");
std::string line;
std::string key;
std::stringstream ss;
while(getline(file,line,'\n'))
{
    ss << line;
    getline(ss,line,',');
    key = line;
    getline(ss,line,'\n');
    m[key] = line;
    ss.clear();
}

Getting data from the file this way guarantees that the data is read correctly now, courtesy of user3389943

Upvotes: 0

user3389943
user3389943

Reputation: 147

while(getline(file,line,','))

The line above is looking for a delimiter ','. However, since line 3 in your file does not have a ',' it effectively reads [Key3\nKey4] as the key.

Hence the error.

Since you cannot change the file, I would suggest read the entire line with the default delimiter '\n' and then parse from the populated string.

Just to note, however, you will need a sentinel value for Key3 if you want it to exist in the map, or use the map::count() member function to check for existence.

Upvotes: 1

Related Questions