lemon/graph_reader.h
changeset 1917 87d3518d73d8
parent 1901 723b2b81d900
child 1935 67b38d699ea7
equal deleted inserted replaced
7:c2dc12d5f62b 8:9bd64ab18422
   376     return GraphReader<Graph>(fn, g);
   376     return GraphReader<Graph>(fn, g);
   377   }
   377   }
   378 
   378 
   379   /// \brief The undirected graph reader class.
   379   /// \brief The undirected graph reader class.
   380   ///
   380   ///
   381   /// The \c UndirGraphReader class provides the graph input. 
   381   /// The \c UGraphReader class provides the graph input. 
   382   /// Before you read this documentation it might be useful to read the general
   382   /// Before you read this documentation it might be useful to read the general
   383   /// description of  \ref graph-io-page "Graph Input-Output".
   383   /// description of  \ref graph-io-page "Graph Input-Output".
   384   ///
   384   ///
   385   /// If you don't need very sophisticated
   385   /// If you don't need very sophisticated
   386   /// behaviour then you can use the versions of the public function
   386   /// behaviour then you can use the versions of the public function
   388   ///
   388   ///
   389   /// The given file format may contain several maps and labeled nodes or 
   389   /// The given file format may contain several maps and labeled nodes or 
   390   /// edges.
   390   /// edges.
   391   ///
   391   ///
   392   /// If you read a graph you need not read all the maps and items just those
   392   /// If you read a graph you need not read all the maps and items just those
   393   /// that you need. The interface of the \c UndirGraphReader is very similar
   393   /// that you need. The interface of the \c UGraphReader is very similar
   394   /// to the UndirGraphWriter but the reading method does not depend on the
   394   /// to the UGraphWriter but the reading method does not depend on the
   395   /// order of the given commands.
   395   /// order of the given commands.
   396   ///
   396   ///
   397   /// The reader object suppose that each not readed value does not contain 
   397   /// The reader object suppose that each not readed value does not contain 
   398   /// whitespaces, therefore it has some extra possibilities to control how
   398   /// whitespaces, therefore it has some extra possibilities to control how
   399   /// it should skip the values when the string representation contains spaces.
   399   /// it should skip the values when the string representation contains spaces.
   400   ///
   400   ///
   401   /// \code
   401   /// \code
   402   /// UndirGraphReader<UndirListGraph> reader(std::cin, graph);
   402   /// UGraphReader<ListUGraph> reader(std::cin, graph);
   403   /// \endcode
   403   /// \endcode
   404   ///
   404   ///
   405   /// The \c readNodeMap() function reads a map from the \c \@nodeset section.
   405   /// The \c readNodeMap() function reads a map from the \c \@nodeset section.
   406   /// If there is a map that you do not want to read from the file and there is
   406   /// If there is a map that you do not want to read from the file and there is
   407   /// whitespace in the string represenation of the values then you should
   407   /// whitespace in the string represenation of the values then you should
   414   /// reader.skipNodeMap("description", desc);
   414   /// reader.skipNodeMap("description", desc);
   415   ///
   415   ///
   416   /// reader.readNodeMap("color", colorMap);
   416   /// reader.readNodeMap("color", colorMap);
   417   /// \endcode
   417   /// \endcode
   418   ///
   418   ///
   419   /// With the \c readUndirEdgeMap() member function you can give an 
   419   /// With the \c readUEdgeMap() member function you can give an 
   420   /// undir edge map reading command similar to the NodeMaps. 
   420   /// uedge map reading command similar to the NodeMaps. 
   421   ///
   421   ///
   422   /// \code
   422   /// \code
   423   /// reader.readUndirEdgeMap("capacity", capacityMap);
   423   /// reader.readUEdgeMap("capacity", capacityMap);
   424   /// \endcode
   424   /// \endcode
   425   ///
   425   ///
   426   /// The reading of the directed edge maps is just a syntactical sugar.
   426   /// The reading of the directed edge maps is just a syntactical sugar.
   427   /// It reads two undirected edgemaps into a directed edge map. The 
   427   /// It reads two undirected edgemaps into a directed edge map. The 
   428   /// undirected edge maps' name should be start with the \c '+' and the
   428   /// undirected edge maps' name should be start with the \c '+' and the
   430   ///
   430   ///
   431   /// \code
   431   /// \code
   432   /// reader.readEdgeMap("flow", flowMap);
   432   /// reader.readEdgeMap("flow", flowMap);
   433   /// \endcode 
   433   /// \endcode 
   434   ///
   434   ///
   435   /// With \c readNode() and \c readUndirEdge() functions you can read 
   435   /// With \c readNode() and \c readUEdge() functions you can read 
   436   /// labeled Nodes and UndirEdges.
   436   /// labeled Nodes and UEdges.
   437   ///
   437   ///
   438   /// \code
   438   /// \code
   439   /// reader.readNode("source", sourceNode);
   439   /// reader.readNode("source", sourceNode);
   440   /// reader.readNode("target", targetNode);
   440   /// reader.readNode("target", targetNode);
   441   ///
   441   ///
   442   /// reader.readUndirEdge("observed", undirEdge);
   442   /// reader.readUEdge("observed", uEdge);
   443   /// \endcode
   443   /// \endcode
   444   ///
   444   ///
   445   /// With the \c readAttribute() functions you can read an attribute
   445   /// With the \c readAttribute() functions you can read an attribute
   446   /// in a variable. You can specify the reader for the attribute as
   446   /// in a variable. You can specify the reader for the attribute as
   447   /// the nodemaps.
   447   /// the nodemaps.
   453   /// reader.run();
   453   /// reader.run();
   454   /// \endcode
   454   /// \endcode
   455   ///
   455   ///
   456   /// \see GraphReader
   456   /// \see GraphReader
   457   /// \see DefaultReaderTraits
   457   /// \see DefaultReaderTraits
   458   /// \see \ref UndirGraphWriter
   458   /// \see \ref UGraphWriter
   459   /// \see \ref graph-io-page
   459   /// \see \ref graph-io-page
   460   ///
   460   ///
   461   /// \author Balazs Dezso
   461   /// \author Balazs Dezso
   462   template <typename _Graph, typename _ReaderTraits = DefaultReaderTraits> 
   462   template <typename _Graph, typename _ReaderTraits = DefaultReaderTraits> 
   463   class UndirGraphReader {
   463   class UGraphReader {
   464   public:
   464   public:
   465     
   465     
   466     typedef _Graph Graph;
   466     typedef _Graph Graph;
   467     typedef typename Graph::Node Node;
   467     typedef typename Graph::Node Node;
   468     typedef typename Graph::Edge Edge;
   468     typedef typename Graph::Edge Edge;
   469     typedef typename Graph::UndirEdge UndirEdge;
   469     typedef typename Graph::UEdge UEdge;
   470 
   470 
   471     typedef _ReaderTraits ReaderTraits;
   471     typedef _ReaderTraits ReaderTraits;
   472     typedef typename ReaderTraits::Skipper DefaultSkipper;
   472     typedef typename ReaderTraits::Skipper DefaultSkipper;
   473 
   473 
   474     /// \brief Construct a new UndirGraphReader.
   474     /// \brief Construct a new UGraphReader.
   475     ///
   475     ///
   476     /// Construct a new UndirGraphReader. It reads into the given graph
   476     /// Construct a new UGraphReader. It reads into the given graph
   477     /// and it use the given reader as the default skipper.
   477     /// and it use the given reader as the default skipper.
   478     UndirGraphReader(std::istream& _is, Graph& _graph, 
   478     UGraphReader(std::istream& _is, Graph& _graph, 
   479 		     const DefaultSkipper& _skipper = DefaultSkipper()) 
   479 		     const DefaultSkipper& _skipper = DefaultSkipper()) 
   480       : reader(new LemonReader(_is)), own_reader(true), skipper(_skipper),
   480       : reader(new LemonReader(_is)), own_reader(true), skipper(_skipper),
   481 	nodeset_reader(*reader, _graph, std::string(), skipper),
   481 	nodeset_reader(*reader, _graph, std::string(), skipper),
   482 	undir_edgeset_reader(*reader, _graph, nodeset_reader, 
   482 	u_edgeset_reader(*reader, _graph, nodeset_reader, 
   483 			     std::string(), skipper),
   483 			     std::string(), skipper),
   484 	node_reader(*reader, nodeset_reader, std::string()),
   484 	node_reader(*reader, nodeset_reader, std::string()),
   485 	undir_edge_reader(*reader, undir_edgeset_reader, std::string()),
   485 	u_edge_reader(*reader, u_edgeset_reader, std::string()),
   486 	attribute_reader(*reader, std::string()) {}
   486 	attribute_reader(*reader, std::string()) {}
   487 
   487 
   488     /// \brief Construct a new UndirGraphReader.
   488     /// \brief Construct a new UGraphReader.
   489     ///
   489     ///
   490     /// Construct a new UndirGraphReader. It reads into the given graph
   490     /// Construct a new UGraphReader. It reads into the given graph
   491     /// and it use the given reader as the default skipper.
   491     /// and it use the given reader as the default skipper.
   492     UndirGraphReader(const std::string& _filename, Graph& _graph, 
   492     UGraphReader(const std::string& _filename, Graph& _graph, 
   493 		     const DefaultSkipper& _skipper = DefaultSkipper()) 
   493 		     const DefaultSkipper& _skipper = DefaultSkipper()) 
   494       : reader(new LemonReader(_filename)), own_reader(true), 
   494       : reader(new LemonReader(_filename)), own_reader(true), 
   495 	skipper(_skipper),
   495 	skipper(_skipper),
   496 	nodeset_reader(*reader, _graph, std::string(), skipper),
   496 	nodeset_reader(*reader, _graph, std::string(), skipper),
   497 	undir_edgeset_reader(*reader, _graph, nodeset_reader, 
   497 	u_edgeset_reader(*reader, _graph, nodeset_reader, 
   498 			     std::string(), skipper),
   498 			     std::string(), skipper),
   499 	node_reader(*reader, nodeset_reader, std::string()),
   499 	node_reader(*reader, nodeset_reader, std::string()),
   500 	undir_edge_reader(*reader, undir_edgeset_reader, std::string()),
   500 	u_edge_reader(*reader, u_edgeset_reader, std::string()),
   501 	attribute_reader(*reader, std::string()) {}
   501 	attribute_reader(*reader, std::string()) {}
   502 
   502 
   503     /// \brief Construct a new UndirGraphReader.
   503     /// \brief Construct a new UGraphReader.
   504     ///
   504     ///
   505     /// Construct a new UndirGraphReader. It reads into the given graph
   505     /// Construct a new UGraphReader. It reads into the given graph
   506     /// and it use the given reader as the default skipper.
   506     /// and it use the given reader as the default skipper.
   507     UndirGraphReader(LemonReader& _reader, Graph& _graph, 
   507     UGraphReader(LemonReader& _reader, Graph& _graph, 
   508 		     const DefaultSkipper& _skipper = DefaultSkipper()) 
   508 		     const DefaultSkipper& _skipper = DefaultSkipper()) 
   509       : reader(_reader), own_reader(false), skipper(_skipper),
   509       : reader(_reader), own_reader(false), skipper(_skipper),
   510 	nodeset_reader(*reader, _graph, std::string(), skipper),
   510 	nodeset_reader(*reader, _graph, std::string(), skipper),
   511 	undir_edgeset_reader(*reader, _graph, nodeset_reader, 
   511 	u_edgeset_reader(*reader, _graph, nodeset_reader, 
   512 			     std::string(), skipper),
   512 			     std::string(), skipper),
   513 	node_reader(*reader, nodeset_reader, std::string()),
   513 	node_reader(*reader, nodeset_reader, std::string()),
   514 	undir_edge_reader(*reader, undir_edgeset_reader, std::string()),
   514 	u_edge_reader(*reader, u_edgeset_reader, std::string()),
   515 	attribute_reader(*reader, std::string()) {}
   515 	attribute_reader(*reader, std::string()) {}
   516 
   516 
   517     /// \brief Destruct the graph reader.
   517     /// \brief Destruct the graph reader.
   518     ///
   518     ///
   519     /// Destruct the graph reader.
   519     /// Destruct the graph reader.
   520     ~UndirGraphReader() {
   520     ~UGraphReader() {
   521       if (own_reader) 
   521       if (own_reader) 
   522 	delete reader;
   522 	delete reader;
   523     }
   523     }
   524 
   524 
   525     /// \brief Give a new node map reading command to the reader.
   525     /// \brief Give a new node map reading command to the reader.
   526     ///
   526     ///
   527     /// Give a new node map reading command to the reader.
   527     /// Give a new node map reading command to the reader.
   528     template <typename Map>
   528     template <typename Map>
   529     UndirGraphReader& readNodeMap(std::string name, Map& map) {
   529     UGraphReader& readNodeMap(std::string name, Map& map) {
   530       nodeset_reader.readNodeMap(name, map);
   530       nodeset_reader.readNodeMap(name, map);
   531       return *this;
   531       return *this;
   532     }
   532     }
   533 
   533 
   534     template <typename Map>
   534     template <typename Map>
   535     UndirGraphReader& readNodeMap(std::string name, const Map& map) {
   535     UGraphReader& readNodeMap(std::string name, const Map& map) {
   536       nodeset_reader.readNodeMap(name, map);
   536       nodeset_reader.readNodeMap(name, map);
   537       return *this;
   537       return *this;
   538     }
   538     }
   539 
   539 
   540     /// \brief Give a new node map reading command to the reader.
   540     /// \brief Give a new node map reading command to the reader.
   541     ///
   541     ///
   542     /// Give a new node map reading command to the reader.
   542     /// Give a new node map reading command to the reader.
   543     template <typename Reader, typename Map>
   543     template <typename Reader, typename Map>
   544     UndirGraphReader& readNodeMap(std::string name, Map& map, 
   544     UGraphReader& readNodeMap(std::string name, Map& map, 
   545 				  const Reader& reader = Reader()) {
   545 				  const Reader& reader = Reader()) {
   546       nodeset_reader.readNodeMap(name, map, reader);
   546       nodeset_reader.readNodeMap(name, map, reader);
   547       return *this;
   547       return *this;
   548     }
   548     }
   549 
   549 
   550     template <typename Reader, typename Map>
   550     template <typename Reader, typename Map>
   551     UndirGraphReader& readNodeMap(std::string name, const Map& map, 
   551     UGraphReader& readNodeMap(std::string name, const Map& map, 
   552 				  const Reader& reader = Reader()) {
   552 				  const Reader& reader = Reader()) {
   553       nodeset_reader.readNodeMap(name, map, reader);
   553       nodeset_reader.readNodeMap(name, map, reader);
   554       return *this;
   554       return *this;
   555     }
   555     }
   556 
   556 
   557     /// \brief Give a new node map skipping command to the reader.
   557     /// \brief Give a new node map skipping command to the reader.
   558     ///
   558     ///
   559     /// Give a new node map skipping command to the reader.
   559     /// Give a new node map skipping command to the reader.
   560     template <typename Reader>
   560     template <typename Reader>
   561     UndirGraphReader& skipNodeMap(std::string name, 
   561     UGraphReader& skipNodeMap(std::string name, 
   562 			     const Reader& reader = Reader()) {
   562 			     const Reader& reader = Reader()) {
   563       nodeset_reader.skipNodeMap(name, reader);
   563       nodeset_reader.skipNodeMap(name, reader);
   564       return *this;
   564       return *this;
   565     }
   565     }
   566 
   566 
   567     /// \brief Give a new undirected edge map reading command to the reader.
   567     /// \brief Give a new undirected edge map reading command to the reader.
   568     ///
   568     ///
   569     /// Give a new undirected edge map reading command to the reader.
   569     /// Give a new undirected edge map reading command to the reader.
   570     template <typename Map>
   570     template <typename Map>
   571     UndirGraphReader& readUndirEdgeMap(std::string name, Map& map) { 
   571     UGraphReader& readUEdgeMap(std::string name, Map& map) { 
   572       undir_edgeset_reader.readUndirEdgeMap(name, map);
   572       u_edgeset_reader.readUEdgeMap(name, map);
   573       return *this;
   573       return *this;
   574     }
   574     }
   575 
   575 
   576     template <typename Map>
   576     template <typename Map>
   577     UndirGraphReader& readUndirEdgeMap(std::string name, const Map& map) { 
   577     UGraphReader& readUEdgeMap(std::string name, const Map& map) { 
   578       undir_edgeset_reader.readUndirEdgeMap(name, map);
   578       u_edgeset_reader.readUEdgeMap(name, map);
   579       return *this;
   579       return *this;
   580     }
   580     }
   581 
   581 
   582 
   582 
   583     /// \brief Give a new undirected edge map reading command to the reader.
   583     /// \brief Give a new undirected edge map reading command to the reader.
   584     ///
   584     ///
   585     /// Give a new undirected edge map reading command to the reader.
   585     /// Give a new undirected edge map reading command to the reader.
   586     template <typename Reader, typename Map>
   586     template <typename Reader, typename Map>
   587     UndirGraphReader& readUndirEdgeMap(std::string name, Map& map,
   587     UGraphReader& readUEdgeMap(std::string name, Map& map,
   588 				       const Reader& reader = Reader()) {
   588 				       const Reader& reader = Reader()) {
   589       undir_edgeset_reader.readUndirEdgeMap(name, map, reader);
   589       u_edgeset_reader.readUEdgeMap(name, map, reader);
   590       return *this;
   590       return *this;
   591     }
   591     }
   592 
   592 
   593     template <typename Reader, typename Map>
   593     template <typename Reader, typename Map>
   594     UndirGraphReader& readUndirEdgeMap(std::string name, const Map& map,
   594     UGraphReader& readUEdgeMap(std::string name, const Map& map,
   595 				       const Reader& reader = Reader()) {
   595 				       const Reader& reader = Reader()) {
   596       undir_edgeset_reader.readUndirEdgeMap(name, map, reader);
   596       u_edgeset_reader.readUEdgeMap(name, map, reader);
   597       return *this;
   597       return *this;
   598     }
   598     }
   599 
   599 
   600     /// \brief Give a new undirected edge map skipping command to the reader.
   600     /// \brief Give a new undirected edge map skipping command to the reader.
   601     ///
   601     ///
   602     /// Give a new undirected edge map skipping command to the reader.
   602     /// Give a new undirected edge map skipping command to the reader.
   603     template <typename Reader>
   603     template <typename Reader>
   604     UndirGraphReader& skipUndirEdgeMap(std::string name,
   604     UGraphReader& skipUEdgeMap(std::string name,
   605 				       const Reader& reader = Reader()) {
   605 				       const Reader& reader = Reader()) {
   606       undir_edgeset_reader.skipUndirMap(name, reader);
   606       u_edgeset_reader.skipUMap(name, reader);
   607       return *this;
   607       return *this;
   608     }
   608     }
   609 
   609 
   610 
   610 
   611     /// \brief Give a new edge map reading command to the reader.
   611     /// \brief Give a new edge map reading command to the reader.
   612     ///
   612     ///
   613     /// Give a new edge map reading command to the reader.
   613     /// Give a new edge map reading command to the reader.
   614     template <typename Map>
   614     template <typename Map>
   615     UndirGraphReader& readEdgeMap(std::string name, Map& map) { 
   615     UGraphReader& readEdgeMap(std::string name, Map& map) { 
   616       undir_edgeset_reader.readEdgeMap(name, map);
   616       u_edgeset_reader.readEdgeMap(name, map);
   617       return *this;
   617       return *this;
   618     }
   618     }
   619 
   619 
   620     template <typename Map>
   620     template <typename Map>
   621     UndirGraphReader& readEdgeMap(std::string name, const Map& map) { 
   621     UGraphReader& readEdgeMap(std::string name, const Map& map) { 
   622       undir_edgeset_reader.readEdgeMap(name, map);
   622       u_edgeset_reader.readEdgeMap(name, map);
   623       return *this;
   623       return *this;
   624     }
   624     }
   625 
   625 
   626 
   626 
   627     /// \brief Give a new edge map reading command to the reader.
   627     /// \brief Give a new edge map reading command to the reader.
   628     ///
   628     ///
   629     /// Give a new edge map reading command to the reader.
   629     /// Give a new edge map reading command to the reader.
   630     template <typename Reader, typename Map>
   630     template <typename Reader, typename Map>
   631     UndirGraphReader& readEdgeMap(std::string name, Map& map,
   631     UGraphReader& readEdgeMap(std::string name, Map& map,
   632 				       const Reader& reader = Reader()) {
   632 				       const Reader& reader = Reader()) {
   633       undir_edgeset_reader.readEdgeMap(name, map, reader);
   633       u_edgeset_reader.readEdgeMap(name, map, reader);
   634       return *this;
   634       return *this;
   635     }
   635     }
   636 
   636 
   637     template <typename Reader, typename Map>
   637     template <typename Reader, typename Map>
   638     UndirGraphReader& readEdgeMap(std::string name, const Map& map,
   638     UGraphReader& readEdgeMap(std::string name, const Map& map,
   639 				       const Reader& reader = Reader()) {
   639 				       const Reader& reader = Reader()) {
   640       undir_edgeset_reader.readEdgeMap(name, map, reader);
   640       u_edgeset_reader.readEdgeMap(name, map, reader);
   641       return *this;
   641       return *this;
   642     }
   642     }
   643 
   643 
   644     /// \brief Give a new edge map skipping command to the reader.
   644     /// \brief Give a new edge map skipping command to the reader.
   645     ///
   645     ///
   646     /// Give a new edge map skipping command to the reader.
   646     /// Give a new edge map skipping command to the reader.
   647     template <typename Reader>
   647     template <typename Reader>
   648     UndirGraphReader& skipEdgeMap(std::string name,
   648     UGraphReader& skipEdgeMap(std::string name,
   649 				       const Reader& reader = Reader()) {
   649 				       const Reader& reader = Reader()) {
   650       undir_edgeset_reader.skipEdgeMap(name, reader);
   650       u_edgeset_reader.skipEdgeMap(name, reader);
   651       return *this;
   651       return *this;
   652     }
   652     }
   653 
   653 
   654     /// \brief Give a new labeled node reading command to the reader.
   654     /// \brief Give a new labeled node reading command to the reader.
   655     ///
   655     ///
   656     /// Give a new labeled node reading command to the reader.
   656     /// Give a new labeled node reading command to the reader.
   657     UndirGraphReader& readNode(std::string name, Node& node) {
   657     UGraphReader& readNode(std::string name, Node& node) {
   658       node_reader.readNode(name, node);
   658       node_reader.readNode(name, node);
   659       return *this;
   659       return *this;
   660     }
   660     }
   661 
   661 
   662     /// \brief Give a new labeled edge reading command to the reader.
   662     /// \brief Give a new labeled edge reading command to the reader.
   663     ///
   663     ///
   664     /// Give a new labeled edge reading command to the reader.
   664     /// Give a new labeled edge reading command to the reader.
   665     UndirGraphReader& readEdge(std::string name, Edge& edge) {
   665     UGraphReader& readEdge(std::string name, Edge& edge) {
   666       undir_edge_reader.readEdge(name, edge);
   666       u_edge_reader.readEdge(name, edge);
   667     }
   667     }
   668 
   668 
   669     /// \brief Give a new labeled undirected edge reading command to the
   669     /// \brief Give a new labeled undirected edge reading command to the
   670     /// reader.
   670     /// reader.
   671     ///
   671     ///
   672     /// Give a new labeled undirected edge reading command to the reader.
   672     /// Give a new labeled undirected edge reading command to the reader.
   673     UndirGraphReader& readUndirEdge(std::string name, UndirEdge& edge) {
   673     UGraphReader& readUEdge(std::string name, UEdge& edge) {
   674       undir_edge_reader.readUndirEdge(name, edge);
   674       u_edge_reader.readUEdge(name, edge);
   675     }
   675     }
   676 
   676 
   677     /// \brief Give a new attribute reading command.
   677     /// \brief Give a new attribute reading command.
   678     ///
   678     ///
   679     ///  Give a new attribute reading command.
   679     ///  Give a new attribute reading command.
   680     template <typename Value>
   680     template <typename Value>
   681     UndirGraphReader& readAttribute(std::string name, Value& value) {
   681     UGraphReader& readAttribute(std::string name, Value& value) {
   682       attribute_reader.readAttribute(name, value);
   682       attribute_reader.readAttribute(name, value);
   683       return *this;
   683       return *this;
   684     }
   684     }
   685     
   685     
   686     /// \brief Give a new attribute reading command.
   686     /// \brief Give a new attribute reading command.
   687     ///
   687     ///
   688     ///  Give a new attribute reading command.
   688     ///  Give a new attribute reading command.
   689     template <typename Reader, typename Value>
   689     template <typename Reader, typename Value>
   690     UndirGraphReader& readAttribute(std::string name, Value& value, 
   690     UGraphReader& readAttribute(std::string name, Value& value, 
   691 			       const Reader& reader) {
   691 			       const Reader& reader) {
   692       attribute_reader.readAttribute<Reader>(name, value, reader);
   692       attribute_reader.readAttribute<Reader>(name, value, reader);
   693       return *this;
   693       return *this;
   694     }
   694     }
   695 
   695 
   714     /// \brief Returns true if the reader can give back the items by its label.
   714     /// \brief Returns true if the reader can give back the items by its label.
   715     ///
   715     ///
   716     /// \brief Returns true if the reader can give back the items by its label.
   716     /// \brief Returns true if the reader can give back the items by its label.
   717     bool isLabelReader() const {
   717     bool isLabelReader() const {
   718       return nodeset_reader.isLabelReader() && 
   718       return nodeset_reader.isLabelReader() && 
   719         undir_edgeset_reader.isLabelReader();
   719         u_edgeset_reader.isLabelReader();
   720     }
   720     }
   721 
   721 
   722     /// \brief Gives back the node by its label.
   722     /// \brief Gives back the node by its label.
   723     ///
   723     ///
   724     /// It reads an label from the stream and gives back which node belongs to
   724     /// It reads an label from the stream and gives back which node belongs to
   730     /// \brief Gives back the edge by its label.
   730     /// \brief Gives back the edge by its label.
   731     ///
   731     ///
   732     /// It reads an label from the stream and gives back which edge belongs to
   732     /// It reads an label from the stream and gives back which edge belongs to
   733     /// it. It is possible only if there was read an "label" named edge map.
   733     /// it. It is possible only if there was read an "label" named edge map.
   734     void readLabel(std::istream& is, Edge& edge) const {
   734     void readLabel(std::istream& is, Edge& edge) const {
   735       return undir_edgeset_reader.readLabel(is, edge);
   735       return u_edgeset_reader.readLabel(is, edge);
   736     } 
   736     } 
   737 
   737 
   738     /// \brief Gives back the undirected edge by its label.
   738     /// \brief Gives back the undirected edge by its label.
   739     ///
   739     ///
   740     /// It reads an label from the stream and gives back which undirected edge 
   740     /// It reads an label from the stream and gives back which undirected edge 
   741     /// belongs to it. It is possible only if there was read an "label" named 
   741     /// belongs to it. It is possible only if there was read an "label" named 
   742     /// edge map.
   742     /// edge map.
   743     void readLabel(std::istream& is, UndirEdge& uedge) const {
   743     void readLabel(std::istream& is, UEdge& uedge) const {
   744       return undir_edgeset_reader.readLabel(is, uedge);
   744       return u_edgeset_reader.readLabel(is, uedge);
   745     } 
   745     } 
   746     
   746     
   747 
   747 
   748   private:
   748   private:
   749 
   749 
   751     bool own_reader;
   751     bool own_reader;
   752 
   752 
   753     DefaultSkipper skipper;
   753     DefaultSkipper skipper;
   754 
   754 
   755     NodeSetReader<Graph, ReaderTraits> nodeset_reader;
   755     NodeSetReader<Graph, ReaderTraits> nodeset_reader;
   756     UndirEdgeSetReader<Graph, ReaderTraits> undir_edgeset_reader;
   756     UEdgeSetReader<Graph, ReaderTraits> u_edgeset_reader;
   757 
   757 
   758     NodeReader<Graph> node_reader;
   758     NodeReader<Graph> node_reader;
   759     UndirEdgeReader<Graph> undir_edge_reader;
   759     UEdgeReader<Graph> u_edge_reader;
   760     
   760     
   761     AttributeReader<ReaderTraits> attribute_reader;
   761     AttributeReader<ReaderTraits> attribute_reader;
   762   };
   762   };
   763 
   763 
   764   /// \brief Read an undirected graph from the input.
   764   /// \brief Read an undirected graph from the input.
   765   ///
   765   ///
   766   /// It is a helper function to read an undirected graph from the given input
   766   /// It is a helper function to read an undirected graph from the given input
   767   /// stream. It gives back an UndirGraphReader object and this object
   767   /// stream. It gives back an UGraphReader object and this object
   768   /// can read more maps, labeled nodes, edges, undirected edges and
   768   /// can read more maps, labeled nodes, edges, undirected edges and
   769   /// attributes.
   769   /// attributes.
   770   ///
   770   ///
   771   /// \warning Do not forget to call the \c run() function.
   771   /// \warning Do not forget to call the \c run() function.
   772   ///
   772   ///
   773   /// \param is The input stream.
   773   /// \param is The input stream.
   774   /// \param g The graph.
   774   /// \param g The graph.
   775   template<typename Graph>
   775   template<typename Graph>
   776   UndirGraphReader<Graph> undirGraphReader(std::istream& is, Graph &g) {
   776   UGraphReader<Graph> uGraphReader(std::istream& is, Graph &g) {
   777     return GraphReader<Graph>(is, g);
   777     return GraphReader<Graph>(is, g);
   778   }
   778   }
   779 
   779 
   780   /// \brief Read an undirected graph from the input.
   780   /// \brief Read an undirected graph from the input.
   781   ///
   781   ///
   782   /// It is a helper function to read an undirected graph from the given input
   782   /// It is a helper function to read an undirected graph from the given input
   783   /// file. It gives back an UndirGraphReader object and this object
   783   /// file. It gives back an UGraphReader object and this object
   784   /// can read more maps, labeled nodes, edges, undirected edges and 
   784   /// can read more maps, labeled nodes, edges, undirected edges and 
   785   /// attributes.
   785   /// attributes.
   786   ///
   786   ///
   787   /// \warning Do not forget to call the \c run() function.
   787   /// \warning Do not forget to call the \c run() function.
   788   ///
   788   ///
   789   /// \param fn The input filename.
   789   /// \param fn The input filename.
   790   /// \param g The graph.
   790   /// \param g The graph.
   791   template<typename Graph>
   791   template<typename Graph>
   792   UndirGraphReader<Graph> undirGraphReader(const std::string& fn, Graph &g) {
   792   UGraphReader<Graph> uGraphReader(const std::string& fn, Graph &g) {
   793     return GraphReader<Graph>(fn, g);
   793     return GraphReader<Graph>(fn, g);
   794   }
   794   }
   795 
   795 
   796   /// @}
   796   /// @}
   797 }
   797 }