Welcome to HBH! If you had an account on hellboundhacker.org you will need to reset your password using the Lost Password system before you will be able to login.

problem outputting through ofstream within a class method (c++). {SOLVED}


Xunxen's Avatar
Member
0 0

I was hoping one of you could tell me why this code works:

#include"armor.h"
#include<string>
#include<iostream>
#include<fstream>
using namespace std;

int main(){
      Armor chainmail(Armor::chest, Armor::forged, string("Chain mail"),
      string("A relatively light but strong chainmail chest armor."));
      try{
            ofstream cm("Chain Mail");//set filename outside function
            chainmail.gainExp(0,cm);
      } catch(string e){
            cout << e << endl;
      }

}
//from armor.cpp
void Armor::gainExp(uint64_t exp,std::ofstream& out){
//unnecessary code for question
     if(!out)
           throw std::string("File could not be opened.");
     out << stats.name << std::endl;
     out << stats.description << std::endl;
     out << stats.def << " " << stats.php << " " << stats.shp;
     out << std::endl;
//etc.
     out.close();
}

While this neither works nor causes any kind of error:

#include<string>
#include<iostream>
#include<fstream>
using namespace std;

int main(){
      Armor chainmail(Armor::chest, Armor::forged, string("Chain mail"),
      string("A relatively light but strong chainmail chest armor."));
      try{
            ofstream cm;//don't set the file name outside function
            chainmail.gainExp(0,cm);
      } catch(string e){
            cout << e << endl;
      }

}
//from armor.cpp
void Armor::gainExp(uint64_t exp,std::ofstream& out){
//unnecessary code for question
out.open(stats.name.c_str());//open file within function
    if(!out)
           throw std::string("File could not be opened.");
    out << stats.name << std::endl;
    out << stats.description << std::endl;
    out << stats.def << " " << stats.php << " " << stats.shp;
    out << std::endl;
//etc.
    out.close();
}

I could not get the file to be created at all from within the function (I even tried declaring and initializing the ofstream object within the function).

as a side question, could someone explain why it won't actually write to the file? do I need to add std::ios::trunc to the open mode bitmask, or open it with only std::ios::out then close it before trying to write to it?


lostrozzacavalli's Avatar
Member
0 0

I would expect "stats.name.c_str()" to be a non-valid file name, as there's no problem using ofstream.open() in a function like you did.

But anyway, to check the error you have to do:

markupif(!out.is_open())

instead of:

markupif(!out)

That's what you would have done with a c FILE*, but using a reference you are already "pointing" to a fully created object, so checking for its validity would lead to nowhere.


Xunxen's Avatar
Member
0 0

I actually had it using out.is_open() before and the same thing was happening. If I use the constructor outside the member function and pass the ofstream object to the method, it creates the file but doesn't write to it. if I use the constructor inside the member method, or try to use the the open method with the filename and openmode, it fails to even create the file. I'm sure the not writing is something on my part, but I can't understand why it fails to do anything with the file. it's clearly opening, or the program should throw an exception, unless I should check out.good(), too…

Also, as a test case, I've tried running the program when the file does exist and it still fails to do anything. The file is still 0 bytes.

and the open/constructor methods of ofstream only require a const char* type. c_str() returns const char*. I don't think I've ever had a problem with this before, but I think I'm going to test that now…


lostrozzacavalli's Avatar
Member
0 0

Then the only things that come to my mind now is that it's not a programming problem but an OS problem, I mean maybe you're trying to modify that file in a folder in which you're not allowed to do so.


Xunxen's Avatar
Member
0 0

I'm afraid that doesn't seem to be the case. I can create and write to a file in this directory with the following code:

#include<string>
#include<fstream>
using namespace std;

int main(){

struct dat{
string a;
}d;

d.a="test";
ofstream out(d.a.c_str(),ios::binary|ios::out);
out << "Test chars" << endl;
out << 123456789 << endl;
out.close();

}

ghost's Avatar
0 0

Xunxen wrote: I'm afraid that doesn't seem to be the case. It wouldn't be the case either way, is_open() would return false since it cannot open an ofstream if it is unable to write to it.


Xunxen's Avatar
Member
0 0

Well, Like I said, it was something I did. I somehow missed that I was trying to write to the file from within a loop that would never run without passing at least 50 as an argument to the method. This thread can be disregarded now.