Search code examples
c++operator-overloadingofstreamostreamstack-memory

unable to overload ofstream operator due to - cannot bind to value of unrelated type (stroustrup c++ chapter 10)


Background:

I am working my way though Stroustrup's c++ book. I am on chapter 10 completing the drills and come across a problem. Now, as far as I can tell I am not strictly following the book, based on how I have seen others answer the questions. I guess Im just after a little more understanding on how to implement the code.

My general aim is to have a write function rather than have it in main().

The aim of the following function is to return an ofstream.

ofstream& c_data_file()
{
    string oname = "mydata.txt";
    ofstream ost {oname};
    if (!ost) {
        string error = "cannot open " + oname;
        throw runtime_error(error);
    }
    return ost;
}

This code does come with a warning from the compiler and I am including it, as it may be related to the problem. The warning is:

Reference to stack memory associated with local variable 'ost' returned

ostream& operator<<(ostream& os, const Point& p)
{
    return os << "(" << p.x <<"," <<p.y <<")";
}

ofstream& operator<<(ofstream& ost, const Point& p)
{
    return ost << "(" << p.x <<"," <<p.y <<")";
}

the ostream works fine (i use this stream else where). The ofstream does not work, returning the error:

Non-const lvalue reference to type 'ofstream' (aka 'basic_ofstream') cannot bind to a value of unrelated type 'basic_ostream >'

The following is the rest of the relevant code:

int main() {

    vector<Point> original_points;
 ofstream& ost = c_data_file();
    for (int i = 0; i<original_points.size(); i++) {
        ost << original_points[i] << "\n";
    }
    ost.close();
}

I have been looking online all day, the following question seems the closet:

overloaded operator << on ofstream concatenation problems

However, i find it hard to understand the answer and from what i do understand it does not solve my issue.

Thank you for reading and for any help you can give.

I am including the following edit here as well as my response to iksemyonov with the hope to clearly express the problem for everyone. Edit1: The warning was resolved following advice from TBBle. The main issue still stands, as the link indicates and iksemyonov suggests I should use ostream instead of ofstream. This is problematic. Ostream is (following the book) used to send data to cout which is what i am doing (code not present). I also want to send the same data to a file (ideally as the book suggests via ofstream).

Edit 2: following the link and iksemyonov's suggestions worked. A number of the comments below helped me execute the suggestions. So thank you to everyone who commented.


Solution

  • Based on the link provided by OP,

    overloaded operator << on ofstream concatenation problems

    other than fixing the returning reference to temporary error, the fix is to change

    ofstream& operator<<(ofstream& ost, const Point& p)
    {
        return ost << "(" << p.x <<"," <<p.y <<")";
    }
    

    to

    ostream& operator<<(ostream& ost, const Point& p)
    {
        return ost << "(" << p.x <<"," <<p.y <<")";
    }
    

    which compiles just fine. As the answer in the link describes, the reason for the error to occur is that ost << "(" returns an object of type ostream, and the further calls to operator<< thus fail because of the incompatibility reported by the compiler.

    On a side note, it is not a good style to not return an exit code from main, as in return 0.