Problems iterating through a map

I snipped the offending code out of the project here:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
string key, value, buffer;
map<string, string> configMap;

while (getline(configFile, buffer)) {
	if (!buffer.find('=')) {
		continue;
	} else {
		key = buffer.substr(0, buffer.find('='));
		value = buffer.erase(0, buffer.find('=') + 1);
		configMap[key] = value;
	}
}

for (auto& iter : configMap) {
	cout << iter.first << " " << iter.second << endl;
	if ("output_file_prefix" == iter.first); istringstream(iter.second) >> basename;
}

cout << "basename is " << basename << endl;


and the offending input file is:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
output_file_prefix= 	Out_test1  	Default= input_file_prefix 	description= suffix for all ouput file names //Note: Output files have above prefix and below suffixes
energy= 		T 		Default= True		 	description= file with list of model energy for each step 
error=	 		T		Defualt= True			description= error messages 
output=			T		Default= True			description= file format with input file format for final model 
bond=			T          Default= True                   description= file with atom and its number of bonds listed
vasp=			T          Default= True                   description= file with final model in vasp format
nn=			T          Default= True                   description= file with atom and its neighbors listed	
atom_type_1=  Si 			Default= none			description= one or two letter character corresponding to atom from periodic table  	example= Si 
atom_type_2= 	H
atom_number_1=		200		Defualt= none			description= number of atoms of type one
atom_number_2= 		20
bond_switch_prob1=	102		Default= none			description= probability atom1 chosen for bond switch; value must be between 0 and 100
bond_switch_prob2= 	0 
atom_switch_code=	F		Default=False			description= function to switch atom types
atoms_to_switch=	Si C 	Default= none 			description= the first atom is switched for the second  example=  Si C 
atoms_switch_prob=	0		Default=none 			description= the probability that bond change is used instead of bond switch; must be between 0 and 100
temperature=		2.5		Default=none			description= temperature in KT units of eV
number_switches=	0		Defualt=0			description= number of switching events created
relax_volume=		T		Default=T			description= relax volume of model
volume_relax_time=	101		Default=0			description= number of accepted switches before volume relaxed
atoms_fixed=			Default=none			description= atom name to fix the position of atoms
lattice_constants=      0. 0. 0.            Default=0 0 0                   description= three reals space seperated for x,y,z lattice lengths in Angstroms; 0 0 0 create lattice based on number and size of atoms

If lattice_constants given, then the format for atoms is:
atom_type atom_number  x1 y1 z1  nbonds  IDa Xa Ya Za  IDb Xb Yb Zb  IDc Xc Yc Zc  IDd Xd Yd Zd


And the output I get is:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
$ ./bam test1.input

If lattice_constants given, then the format for atoms is: If lattice_constants given, then the format for atoms is:
atom_number_1           200             Defualt= none                   description= number of atoms of type one
atom_number_2           20
atom_switch_code        F               Default=False                   description= function to switch atom types
atom_type atom_number  x1 y1 z1  nbonds  IDa Xa Ya Za  IDb Xb Yb Zb  IDc Xc Yc Zc  IDd Xd Yd Zd atom_type atom_number  x1 y1 z1  nbonds  IDa Xa Ya Za  IDb Xb Yb Zb  IDc Xc Yc Zc  IDd Xd Yd Zd
atom_type_1   Si                        Default= none                   description= one or two letter character corresponding to atom from periodic table      example= Si
atom_type_2     H
atoms_fixed                     Default=none                    description= atom name to fix the position of atoms
atoms_switch_prob       0               Default=none                    description= the probability that bond change is used instead of bond switch; must be between 0 and 100
atoms_to_switch         Si C    Default= none                   description= the first atom is switched for the second  example=  Si C
bond                    T          Default= True                   description= file with atom and its number of bonds listed
bond_switch_prob1       102             Default= none                   description= probability atom1 chosen for bond switch; value must be between 0 and 100
bond_switch_prob2       0
energy                  T               Default= True                   description= file with list of model energy for each step
error                   T               Defualt= True                   description= error messages
lattice_constants       0. 0. 0.            Default=0 0 0                   description= three reals space seperated for x,y,z lattice lengths in Angstroms; 0 0 0 create lattice based on number and size of atoms
nn                      T          Default= True                   description= file with atom and its neighbors listed
number_switches         0               Defualt=0                       description= number of switching events created
output                  T               Default= True                   description= file format with input file format for final model
output_file_prefix      Out_test1       Default= input_file_prefix      description= suffix for all ouput file names //Note: Output files have above prefix and below suffixes
relax_volume            T               Default=T                       description= relax volume of model
temperature             2.5             Default=none                    description= temperature in KT units of eV
vasp                    T          Default= True                   description= file with final model in vasp format
volume_relax_time       101             Default=0                       description= number of accepted switches before volume relaxed
basename is 101


when I am expecting:
1
2
...
basename is Out_test1


I can see that it is pulling 101 from the last value of colume_relax_time, but I don't know why. What am I doing wrong?
Last edited on
Remove the semicolon in the middle of line 16 of your first code sample.
It was concluding the if block (which is then empty).

As it stands, istringstream is not inside the if block and so it sends values successively into basename on each pass through the for loop. The map orders itself by the dictionary order of the key, so the last value to be sent to basename is that associated with volume_relax_time, i.e. the value 101. This is what is in there at the end of the for loop and is reported by your code.
Last edited on
you are reading in the rest of the line because you're using getline() that reads the entire line unless stopped earlier by passing it a delimiter.
your file is not uniformly formatted, here I'm looking particularly at the second column of lines 15 and 22 that don't match any of the others - so you need to think of a way of reading these two particular lines separate from the rest.
one (slightly laborious) way might be:
1
2
3
4
//psuedo-codo 
- getline() entire line
- std::istringstream stream(line)
- while (stream >> std::string temp) push_back temp into std::vector<string>

- for all the other lines apart from 15 and 22 the 2nd vector element would give you the map value so you can save this and discard the others through vector.clear()
- for the two 'offending' lines think of how you want to extract the information - whatever you decide it'll still be a bit hackish given the non-uniform nature of the input file
Line 5 should be if (buffer.find('=') == string::npos) {
Topic archived. No new replies allowed.