No compiler at moment to confirm, but try this:
change this line:
ifstream marker;
to this:
ifstream marker("markers.txt")
comment out this line:
marker.open("markers.txt");
and change this line:
marker.close();
to this:
marker.seekg(0, ios::beg);
This is a discussion on Some help for a newbie? within the C++ Programming forums, part of the General Programming Boards category; No compiler at moment to confirm, but try this: change this line: ifstream marker; to this: ifstream marker("markers.txt") comment out ...
No compiler at moment to confirm, but try this:
change this line:
ifstream marker;
to this:
ifstream marker("markers.txt")
comment out this line:
marker.open("markers.txt");
and change this line:
marker.close();
to this:
marker.seekg(0, ios::beg);
Same result
mark still equals "done" after end of first inside loop all the way to the end.
I've added extensive comments and debugging statements to your code. Without sample files and a better understanding of exactly what you are expecting I can't tell why you aren't getting results you want. Following value of mark through program and seeing where value of mark isn't what you expect is firt step to find out where error is. Once located, then solution is sometimes obvious, and sometimes not.
Code:#include <fstream> #include <iostream> #include <string.h> using namespace std; int main() { char original[50]= "duh"; //initialize original char mark[50]; ofstream final("final.txt"); int spotter = 0; int conv; int indicator = 0; ifstream marker("marker.txt"); ifstream starter("original.txt"); //check if any of the files failed to open if(!marker) cout << "failed to open marker file" << endl; if(!starter) cout << "failed to open original file" << endl; if(!original) cout << "failed to open final file" << endl; while(strcmpi(original, "done")) { spotter = spotter + 1; starter >> original; //read in value from original file //confim read in from original cout << "original = " << original << endl; indicator = 0; //marker.open("markers.txt"); marker >> mark; //confirm read in from mark file cout << "mark = " << mark << endl; cout<<"OUTSIDE WHILE LOOP ITERATING"<<endl; while(strcmpi(mark, "done")) { conv = atoi(mark); //confirm conversion of mark cout << "conv = " << conv << endl; cout<<"INSIDE WHILE LOOP ITERATING"<<endl; cout << "spotter = " << spotter << endl; if(conv == spotter) { cout<<"Conv is equal to spotter! Iteration: " << spotter << endl; //read in next item from marker text marker >> mark; cout << "mark now equals " << mark << endl; //starter>>original; //out put latest value of mark to final file final << mark; indicator = 1; break; } //now read in next item in marker file irrespective of whether //conv == spotter marker >> mark; //confirm input into mark cout << "the value of mark to compare to "done" is " << mark << endl; //this loop will stop only if this value of mark is "done" } //inner loop now done. the value of mark should now be "done" cout << "mark should equal done. It is " << mark << endl; //if conv never equaled spotter through that section //of marker file then indicator will be 0 if(indicator == 0) { //in which case, output value of original to final file //rather than some value from marker file final << original; } final<<" "; //don't close marker file //marker.close(); //instead, restart the marker files get pointer back to start of marker file. //don't continue from where the first done was found but research from //beginning of marker file each time through the inner loop marker.seekg(0, ios::beg); //that's a zero, not a capital oh //move on to next item in original file which was read in back at top //of while loop } //when both loops done, both original and mark should be done cout << "both loops done" << endl; cout << "mark = " << mark << endl; cout << "original = " << original << endl; final.close(); marker.close(); starter.close(); cin.get(); return 0; }
I have been doing something like that. I'll copy+paste my code from Dev-C++ and then transcribe the output
Code:
Output:Code:#include <fstream> #include <iostream> #include <string.h> using namespace std; int main() { char original[50]; char mark[50]; ofstream final("final.txt"); int spotter = 0; int conv; int indicator = 0; ifstream marker("markers.txt"); ifstream starter("original.txt"); while(strcmpi(original, "done")) { spotter = spotter + 1; starter>>original; indicator = 0; //marker.open("markers.txt"); marker.seekg(0, ios::beg); marker>>mark; cout<<"Before owl, mark equals "<<mark<<endl; cout<<"OUTSIDE WHILE LOOP ITERATING, spotter equals"<<spotter<<" "<<endl; while(strcmpi(mark, "done")) { conv = atoi(mark); cout<<"String mark is equal to: "<<mark<<" "; cout<<"Integer conv is equal to: "<<conv<<" "; cout<<"INSIDE WHILE LOOP ITERATING "<<endl; if(conv == spotter) { marker>>mark; cout<<"Conv is equal to spotter! Iteration: "<<spotter<<" "<<endl; //starter>>original; final<<mark; indicator = 1; break; } marker>>mark; } if(indicator == 0) final<<original; final<<" "; marker.seekg(0, ios::beg); } final.close(); cin.get(); return 0; cin.get(); }
(by the way, owl is short for outside while loop)
Code:Before owl, mark equals 4 OUTSIDE WHILE LOOP ITERATING, spotter equals1 String mark is equal to: 4 Integer conv is equal to: 4 INSIDE WHILE LOOP ITERATING String mark is equal to: odd Integer conv is equal to: 0 INSIDE WHILE LOOP ITERATING String mark is equal to: 11Integer conv is equal to: 11 INSIDE WHILE LOOP ITERATING String mark is equal to: eat Integer conv is equal to: 0 INSIDE WHILE LOOP ITERATING Before owl, mark equals done OUTSIDE WHILE LOOP ITERATING, spotter equals2 Before owl, mark equals done OUTSIDE WHILE LOOP ITERATING, spotter equals3 Before owl, mark equals done OUTSIDE WHILE LOOP ITERATING, spotter equals4 Before owl, mark equals done OUTSIDE WHILE LOOP ITERATING, spotter equals5 Before owl, mark equals done OUTSIDE WHILE LOOP ITERATING, spotter equals6 Before owl, mark equals done OUTSIDE WHILE LOOP ITERATING, spotter equals7 Before owl, mark equals done OUTSIDE WHILE LOOP ITERATING, spotter equals8 Before owl, mark equals done OUTSIDE WHILE LOOP ITERATING, spotter equals9 Before owl, mark equals done OUTSIDE WHILE LOOP ITERATING, spotter equals10 Before owl, mark equals done OUTSIDE WHILE LOOP ITERATING, spotter equals11 Before owl, mark equals done OUTSIDE WHILE LOOP ITERATING, spotter equals12 Before owl, mark equals done OUTSIDE WHILE LOOP ITERATING, spotter equals13
try running this program and see if output is:
1 2 3
1 2 3
1 2 3
If that's what you get, then post the first 5 entries in original.txt and the first 20 entries in marker.txt so I can try to recreate your files and run your program with your files.Code:#include <fstream> #include <iostream> using namespace std; int main(int argc, char* argv[]) { ofstream fout("marker1.txt"); int i, j, k; for(i = 1; i < 5; ++i) fout << i << ' '; fout.close(); ifstream fin("marker1.txt"); if(!fin) cout << "unable to open marker1.txt" << endl; else cout << "marker1 open" << endl; for(i = 0; i < 3; ++i) { for(j = 0 ; j < 3; ++j) { fin >> k; cout << k << ' '; } cout << endl; fin.seekg(0, ios::beg); } return 0; }
I did indeed get
I'm not sure what you mean by entries (I assume the string until a space?) but I'll just give you the full contents of both files:Code:marker1 open 123 123 123
original.txt:
markers.txt:Code:once upon an adjective dog , a cat decided to verb . done
Code:4 odd 11 eat done
Finally. With the aid of your file inputs and a little tinkering I think I got it to work like you want. Turns out that when marker equals done the terminating char is EOF. EOF causes marker to go into a fail state. This fail state has to be cleared before internal get pointer for marker can be reset using seekg() or by closing and reopening marker---worked either way when I checked it.
To clear the fail state that marker goes into when it reads in done, put the following line right before the call to seekg() (or the call to close() if you prefer).
marker.clear();
BTW, you don't need to call seekg() twice in succession, once will do.
I'm sorry I didn't mention this until now - I had thought about clearing the flags but then forgot about it - but another option that might be better style but less efficient is to declare the marker ifstream inside the main while loop. Declare it like you did originally:
ifstream marker("markers.txt");
Because it is inside the while loop, it will automatically close after each loop iteration (since it goes out of scope). It will also automatically get its flags cleared.
In fact, maybe an even better solution would be to have a map of markers (e.g. 4, 11) to values (e.g. "odd", "eat"). Then just load the map once at the beginning of your program. That way you only have to read the markers.txt file once, and everything is more efficient. Of course, you'd have to know how to use maps, but I would recommend learning the idea behind them at some point soon anyway.
YAY!
Thank you so much, elad and jlou. Both of you have been great help.
I'm sure that this monstrosity of a program I have created is pretty poorly written in terms of design, but...
IT WORKS!