In order to load and save graphs from files, we have
provided two classes derived from ARGLoader
. The
first, BinaryGraphLoader
, is devoted to
unattributed graphs, and adopts the binary file format
employed for the
Graph Database.
The second, StreamARGLoader
, is a template class which
employs C++ input/output streams and overloaded stream
operators to read and write graphs from/to text files.
Both the classes are defined in argloader.h
.
In section VFLib class reference a detailed description of the file formats will be presented. Here we will show some examples of the use of these two classes.
Let us start with BinaryGraphLoader
. The constructor of this
class requires an istream
object, which must be open using
the ios::binary
mode:
#include <iostream>
#include <fstream>
using namespace std;
#include "argraph.h"
#include "argloader.h"
int main()
{ // First, open the file in binary mode
ifstream in("graph.bin", ios::in | ios::binary);
// Second, create a BinaryGraphLoader
BinaryGraphLoader loader(in);
// Now a graph can be constructed
Graph g(&loader);
// ... to be continued ...
A graph, represented either as an object of class Graph
, or
as an ARGLoader
, can be saved in the same format using the
static method write
.
// ... suppose that a graph g has been constructed ...
// Open a binary file
ofstream out("outfile.bin", ios::out | ios::binary);
// Write the graph
GraphBinaryLoader::write(out, g);
// Close the file
out.close();
// ... to be continued ...
Remember that this class does not consider node/edge attributes!
Now, let us turn our attention to StreamARGLoader<N,E>
.
This is a template class for reading and writing graphs with node
attributes of type N
and edge attributes of type E
.
As we have said previously, it is responsibility of the ARGLoader
to allocate the data structures for storing the attributes.
StreamARGLoader
perform this task with the help of an Allocator
instance. Allocator
is an abstract template class which provide
an Allocate
method for creating a new attribute.
The template class NewAllocator
is an implementation of Allocator
that uses the new
operator for allocating the attribute.
Both Allocator
and NewAllocator
are defined in allocpool.h
.
Besides creating a suitable allocator, you need to override the
operator >> for reading graphs and the operator
O.
<<
for writing, if the types of your attributes do not already support stream I
For example, let us reconsider the case in which the node attributes represent points in the plane, and there are no edge attributes.
First, you have to define the attribute classes, with the corresponding I/O operators. Notice that you will need an empty class for the edge attribute.
#include <iostream>
#include <fstream>
#include <argraph.h>
#include <argloader.h>
#include <allocpool.h>
//
// Define class Point, with its I/O operators
//
class Point
{ public:
float x, y;
};
istream& operator>>(istream& in, Point &p)
{ in >> p.x >> p.y;
return in;
}
ostream& operator<<(ostream& out, Point &p)
{ out << p.x << ' ' << p.y;
return out;
}
//
// Define class Empty, with its I/O operators
//
class Empty
{
};
istream& operator>>(istream& in, Empty &)
{ // Do nothing!
return in;
}
ostream& operator<<(ostream& out, Empty &)
{ // Do nothing!
return out;
}
Now, you have first to create the two allocators (one for nodes
and one for edges), and then a StreamARGLoader
object. Notice that
for the edges we have used a NullAllocator
, which does no
allocation at all!
int main()
{ // Create the allocators
NewAllocator<Point> node_allocator;
NullAllocator<Empty> edge_allocator;
// Open the file
ifstream in("graph.txt");
// Create the ARGLoader
StreamARGLoader<Point, Empty> loader(&node_allocator,
&edge_allocator,
in);
// Build the graph
ARGraph<Point, Empty> graph(&loader);
//......
Similarly to the GraphBinaryLoader
class, also StreamARGLoader
provides a static write
method to write out a graph in the
corresponding format:
// ... suppose that a graph g has been constructed ...
// Open a text file
ofstream out("outfile.txt");
// Write the graph
StreamARGLoader::write(out, g);
// Close the file
out.close();
// ... to be continued ...