Apologies for the basic nature of this question … but I’ve scoured the documentation for the Boost Serialization library without any hint of how to solve this.

 

I want to use the Boost Serialization library to allow the saving and loading of a collection of database rows.

 

This will use XML as the file format.

 

All of the examples in the documentation assume that there is a “root” object saved, and in the case of a collection on objects, just save and load the collection itself:

 

void save_mib(const vector<Row>& mib, const string& filename)

{

    ofstream ofs(filename.c_str());

    boost::archive::xml_oarchive oa(ofs);

 

    oa << BOOST_SERIALIZATION_NVP(mib);

}

 

void load_mib(vector<Row>& mib, const string& filename)

{

    ifstream ifs(filename.c_str());

    boost::archive::xml_iarchive ia(ifs);

 

    ia >> BOOST_SERIALIZATION_NVP(mib);

}

 

However, this will be a LARGE collection of rows, and I don’t want to read them all in at once. Instead, I want to read them in, one at a time and process piecemeal. However, I can’t work out from the documentation how to test that there is another row left to read …

 

So, I can successfully output a list of rows:

 

void save_mib(const vector<Row>& mib, const string& filename)

{

    ofstream ofs(filename.c_str());

    boost::archive::xml_oarchive oa(ofs);

 

    const vector<Row>::const_iterator mibEnd(mib.end());

 

    for (vector<Row>::const_iterator i(mib.begin()); i != mibEnd; ++i)

    {

        const Row& row(*i);

       

        oa << BOOST_SERIALIZATION_NVP(row);

    }

}

 

I have not been able to deduce how to read these back in again without relying on there being a “stream error” exception thrown …

 

void load_mib(vector<Row>& mib, const string& filename)

{

    ifstream ifs(filename.c_str());

    boost::archive::xml_iarchive ia(ifs);

 

    Row row;

 

    try

    {

        while (1)

        {

            ia >> BOOST_SERIALIZATION_NVP(row);

            mib.push_back(row);

        }

    }

    catch (boost::archive::archive_exception& ae)

    {

        cout << "caught archive_exception '" << ae.what() << "'\n";

    }

    catch (exception& e)

    {

        cout << "caught exception '" << e.what() << "'\n";

    }

    catch (...)

    {

        cout << "caught unknown exception\n";

    }

}

 

Is that the best way to do it? Surely there is a better, exception-free, method?

 

Also, can anyone please suggest a way of doing this using ostream_iterators and istream_iterators?

 

Thank you for reading this far!

 

Graham.