namespace lemon { /*! \page read_write_bg Background of Reading and Writing To read a map (on the nodes or edges) the \ref lemon::GraphReader "GraphReader" should know how to read a Value from the given map. By the default implementation the input operator reads a value from the stream and the type of the read value is the value type of the given map. When the reader should skip a value in the stream, because you do not want to store it in a map, the reader skips a character sequence without whitespaces. If you want to change the functionality of the reader, you can use template parameters to specialize it. When you give a reading command for a map you can give a Reader type as template parameter. With this template parameter you can control how the Reader reads a value from the stream. The reader has the next structure: \code struct TypeReader { typedef TypeName Value; void read(std::istream& is, Value& value); }; \endcode For example, the \c "strings" nodemap contains strings and you do not need the value of the string just the length. Then you can implement an own Reader struct. \code struct LengthReader { typedef int Value; void read(std::istream& is, Value& value) { std::string tmp; is >> tmp; value = tmp.length(); } }; ... reader.readNodeMap("strings", lengthMap); \endcode The global functionality of the reader class can be changed by giving a special template parameter to the GraphReader class. By default, the template parameter is \c DefaultReaderTraits. A reader traits class should provide a nested template class Reader for each type, and a DefaultReader for skipping a value. The specialization of writing is very similar to that of reading. \section u Undirected graphs In a file describing an undirected graph (ugraph, for short) you find an \c uedgeset section instead of the \c edgeset section. The first line of the section describes the names of the maps on the undirected egdes and all next lines describe one undirected edge with the the incident nodes and the values of the map. The format handles directed edge maps as a syntactical sugar???, if there are two maps with names being the same with a \c '+' and a \c '-' prefix then this will be read as a directed map. \code @uedgeset label capacity +flow -flow 32 2 1 4.3 2.0 0.0 21 21 5 2.6 0.0 2.6 21 12 8 3.4 0.0 0.0 \endcode The \c edges section is changed to \c uedges section. This section describes labeled edges and undirected edges. The directed edge label should start with a \c '+' or a \c '-' prefix to decide the direction of the edge. \code @uedges uedge 1 +edge 5 -back 5 \endcode There are similar classes to the \ref lemon::GraphReader "GraphReader" and \ref lemon::GraphWriter "GraphWriter" which handle the undirected graphs. These classes are the \ref lemon::UGraphReader "UGraphReader" and \ref lemon::UGraphWriter "UGraphWriter". The \ref lemon::UGraphReader::readUEdgeMap() "readUEdgeMap()" function reads an undirected map and the \ref lemon::UGraphReader::readUEdge() "readUEdge()" reads an undirected edge from the file, \code reader.readUEdgeMap("capacity", capacityMap); reader.readEdgeMap("flow", flowMap); ... reader.readUEdge("u_edge", u_edge); reader.readEdge("edge", edge); \endcode \section advanced Advanced features The graph reader and writer classes give an easy way to read and write graphs. But sometimes we want more advanced features. In this case we can use the more general lemon reader and writer interface. The LEMON file format is a section oriented file format. It contains one or more sections, each starting with a line identifying its type (the word starting with the \c \@ character). The content of the section this way cannot contain line with \c \@ first character. The file may contains comment lines with \c # first character. The \ref lemon::LemonReader "LemonReader" and \ref lemon::LemonWriter "LemonWriter" gives a framework to read and write sections. There are various section reader and section writer classes which can be attached to a \ref lemon::LemonReader "LemonReader" or a \ref lemon::LemonWriter "LemonWriter". There are default section readers and writers for reading and writing item sets, and labeled items in the graph. These read and write the format described above. Other type of data can be handled with own section reader and writer classes which are inherited from the \c LemonReader::SectionReader or the \ref lemon::LemonWriter::SectionWriter "LemonWriter::SectionWriter" classes. The next example defines a special section reader which reads the \c \@description sections into a string: \code class DescriptionReader : LemonReader::SectionReader { protected: virtual bool header(const std::string& line) { std::istringstream ls(line); std::string head; ls >> head; return head == "@description"; } virtual void read(std::istream& is) { std::string line; while (getline(is, line)) { desc += line; } } public: typedef LemonReader::SectionReader Parent; DescriptionReader(LemonReader& reader) : Parent(reader) {} const std::string& description() const { return description; } private: std::string desc; }; \endcode The other advanced stuff of the generalized file format is that multiple edgesets can be stored to the same nodeset. It can be used for example as a network traffic matrix. In our example there is a network with symmetric links and there are assymetric traffic request on the network. This construction can be stored in an undirected graph and in a directed \c ListEdgeSet class. The example shows the input with the \ref lemon::LemonReader "LemonReader" class: \code ListUGraph network; ListUGraph::UEdgeMap capacity; ListEdgeSet traffic(network); ListEdgeSet::EdgeMap request(network); LemonReader reader(std::cin); NodeSetReader nodesetReader(reader, network); UEdgeSetReader uEdgesetReader(reader, network, nodesetReader); uEdgesetReader.readEdgeMap("capacity", capacity); EdgeSetReader > edgesetReader(reader, traffic, nodesetReader, "traffic"); edgesetReader.readEdgeMap("request", request); reader.run(); \endcode Because both the \ref lemon::GraphReader "GraphReader" and the \ref lemon::UGraphReader "UGraphReader" can be converted to \ref lemon::LemonReader "LemonReader" and it can resolve the label's of the items, the previous result can be achived with the \ref lemon::UGraphReader "UGraphReader" class, too. \code ListUGraph network; ListUGraph::UEdgeSet capacity; ListEdgeSet traffic(network); ListEdgeSet::EdgeMap request(network); UGraphReader reader(std::cin, network); reader.readEdgeMap("capacity", capacity); EdgeSetReader > edgesetReader(reader, traffic, reader, "traffic"); edgesetReader.readEdgeMap("request", request); reader.run(); \endcode \author Balazs Dezso */ }