COIN-OR::LEMON - Graph Library

source: lemon-0.x/lemon/graph_reader.h @ 1588:b79bcba43661

Last change on this file since 1588:b79bcba43661 was 1540:7d028a73d7f2, checked in by athos, 19 years ago

Documented Balazs's stuff. Quite enough of that.

File size: 28.2 KB
Line 
1/* -*- C++ -*-
2 * lemon/graph_reader.h - Part of LEMON, a generic C++ optimization library
3 *
4 * Copyright (C) 2005 Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport
5 * (Egervary Research Group on Combinatorial Optimization, EGRES).
6 *
7 * Permission to use, modify and distribute this software is granted
8 * provided that this copyright notice appears in all copies. For
9 * precise terms see the accompanying LICENSE file.
10 *
11 * This software is provided "AS IS" with no warranty of any kind,
12 * express or implied, and with no claim as to its suitability for any
13 * purpose.
14 *
15 */
16
17///\ingroup io_group
18///\file
19///\brief Lemon Graph Format reader.
20
21#ifndef LEMON_GRAPH_READER_H
22#define LEMON_GRAPH_READER_H
23
24#include <iostream>
25
26#include <lemon/error.h>
27#include <lemon/lemon_reader.h>
28
29namespace lemon {
30
31  /// \addtogroup io_group
32  /// @{
33
34  /// \brief The graph reader class.
35  ///
36  /// The \c GraphReader class provides the graph input.
37  /// Before you read this documentation it might be useful to read the general
38  /// description of  \ref graph-io-page "Graph Input-Output".
39  ///
40  /// If you don't need very sophisticated
41  /// behaviour then you can use the versions of the public function
42  /// \ref readGraph() to read a graph (or a max flow instance etc).
43  ///
44  /// The file to be read may contain several maps and labeled nodes or
45  /// edges.
46  ///
47  /// If you read a graph you need not read all the maps and items just those
48  /// that you need. The interface of the \c GraphReader is very similar to
49  /// the GraphWriter but the reading method does not depend on the order the
50  /// given commands (i.e. you don't have to insist on the order in which the
51  /// maps are given in the file).
52  ///
53  /// The reader object assumes that not readed values do not contain
54  /// whitespaces, therefore it has some extra possibilities to control how
55  /// it should skip the values when the string representation contains spaces.
56  ///
57  /// \code
58  /// GraphReader<ListGraph> reader(std::cin, graph);
59  /// \endcode
60  ///
61  /// The \c readNodeMap() function reads a map from the \c \@nodeset section.
62  /// If there is a map that you do not want to read from the file and there is
63  /// whitespace in the string represenation of the values then you should
64  /// call the \c skipNodeMap() template member function with proper
65  /// parameters.
66  ///
67  /// \code
68  /// reader.readNodeMap("coords", coords);
69  ///
70  /// reader.readNodeMap<QuotedStringReader>("label", labelMap);
71  /// reader.skipNodeMap<QuotedStringReader>("description");
72  ///
73  /// reader.readNodeMap("color", colorMap);
74  /// \endcode
75  ///
76  /// With the \c readEdgeMap() member function you can give an edge map
77  /// reading command similar to the NodeMaps.
78  ///
79  /// \code
80  /// reader.readEdgeMap("weight", weightMap);
81  /// reader.readEdgeMap("label", labelMap);
82  /// \endcode
83  ///
84  /// With \c readNode() and \c readEdge() functions you can read
85  /// labeled Nodes and Edges.
86  ///
87  /// \code
88  /// reader.readNode("source", sourceNode);
89  /// reader.readNode("target", targetNode);
90  ///
91  /// reader.readEdge("observed", edge);
92  /// \endcode
93  ///
94  /// With the \c readAttribute() functions you can read an attribute
95  /// into a variable. You can specify the reader for the attribute as
96  /// the nodemaps.
97  ///
98  /// After you give all read commands you must call the \c run() member
99  /// function, which executes all the commands.
100  ///
101  /// \code
102  /// reader.run();
103  /// \endcode
104  ///
105  /// \see DefaultReaderTraits
106  /// \see QuotedStringReader
107  /// \see \ref GraphWriter
108  /// \see \ref graph-io-page
109  /// \author Balazs Dezso
110  template <typename _Graph, typename _ReaderTraits = DefaultReaderTraits>
111  class GraphReader {
112  public:
113   
114    typedef _Graph Graph;
115    typedef typename Graph::Node Node;
116    typedef typename Graph::Edge Edge;
117
118    typedef _ReaderTraits ReaderTraits;
119    typedef typename ReaderTraits::Skipper DefaultSkipper;
120
121    /// \brief Construct a new GraphReader.
122    ///
123    /// Construct a new GraphReader. It reads into the given graph
124    /// and it uses the given reader as the default skipper.
125    GraphReader(std::istream& _is,
126                typename SmartParameter<Graph>::Type _graph,
127                const DefaultSkipper& _skipper = DefaultSkipper())
128      : reader(new LemonReader(_is)), own_reader(true), skipper(_skipper),
129        nodeset_reader(*reader, _graph, std::string(), skipper),
130        edgeset_reader(*reader, _graph, nodeset_reader,
131                       std::string(), skipper),
132        node_reader(*reader, nodeset_reader, std::string()),
133        edge_reader(*reader, edgeset_reader, std::string()),
134        attribute_reader(*reader, std::string()) {}
135
136    /// \brief Construct a new GraphReader.
137    ///
138    /// Construct a new GraphReader. It reads into the given graph
139    /// and it uses the given reader as the default skipper.
140    GraphReader(const std::string& _filename,
141                typename SmartParameter<Graph>::Type _graph,
142                const DefaultSkipper& _skipper = DefaultSkipper())
143      : reader(new LemonReader(_filename)), own_reader(true),
144        skipper(_skipper),
145        nodeset_reader(*reader, _graph, std::string(), skipper),
146        edgeset_reader(*reader, _graph, nodeset_reader,
147                       std::string(), skipper),
148        node_reader(*reader, nodeset_reader, std::string()),
149        edge_reader(*reader, edgeset_reader, std::string()),
150        attribute_reader(*reader, std::string()) {}
151
152    /// \brief Construct a new GraphReader.
153    ///
154    /// Construct a new GraphReader. It reads into the given graph
155    /// and it uses the given reader as the default skipper.
156    GraphReader(LemonReader& _reader,
157                typename SmartParameter<Graph>::Type _graph,
158                const DefaultSkipper& _skipper = DefaultSkipper())
159      : reader(_reader), own_reader(false), skipper(_skipper),
160        nodeset_reader(*reader, _graph, std::string(), skipper),
161        edgeset_reader(*reader, _graph, nodeset_reader,
162                       std::string(), skipper),
163        node_reader(*reader, nodeset_reader, std::string()),
164        edge_reader(*reader, edgeset_reader, std::string()),
165        attribute_reader(*reader, std::string()) {}
166
167    /// \brief Destruct the graph reader.
168    ///
169    /// Destruct the graph reader.
170    ~GraphReader() {
171      if (own_reader)
172        delete reader;
173    }
174
175    /// \brief Give a new node map reading command to the reader.
176    ///
177    /// Give a new node map reading command to the reader.
178    template <typename Map>
179    GraphReader& readNodeMap(std::string name, Map& map) {
180      nodeset_reader.readNodeMap(name, map);
181      return *this;
182    }
183
184    template <typename Map>
185    GraphReader& readNodeMap(std::string name, const Map& map) {
186      nodeset_reader.readNodeMap(name, map);
187      return *this;
188    }
189
190    /// \brief Give a new node map reading command to the reader.
191    ///
192    /// Give a new node map reading command to the reader.
193    template <typename Reader, typename Map>
194    GraphReader& readNodeMap(std::string name, Map& map,
195                             const Reader& reader = Reader()) {
196      nodeset_reader.readNodeMap(name, map, reader);
197      return *this;
198    }
199
200    template <typename Reader, typename Map>
201    GraphReader& readNodeMap(std::string name, const Map& map,
202                             const Reader& reader = Reader()) {
203      nodeset_reader.readNodeMap(name, map, reader);
204      return *this;
205    }
206
207    /// \brief Give a new node map skipping command to the reader.
208    ///
209    /// Give a new node map skipping command to the reader.
210    template <typename Reader>
211    GraphReader& skipNodeMap(std::string name,
212                             const Reader& reader = Reader()) {
213      nodeset_reader.skipNodeMap(name, reader);
214      return *this;
215    }
216
217    /// \brief Give a new edge map reading command to the reader.
218    ///
219    /// Give a new edge map reading command to the reader.
220    template <typename Map>
221    GraphReader& readEdgeMap(std::string name, Map& map) {
222      edgeset_reader.readEdgeMap(name, map);
223      return *this;
224    }
225
226    template <typename Map>
227    GraphReader& readEdgeMap(std::string name, const Map& map) {
228      edgeset_reader.readEdgeMap(name, map);
229      return *this;
230    }
231
232
233    /// \brief Give a new edge map reading command to the reader.
234    ///
235    /// Give a new edge map reading command to the reader.
236    template <typename Reader, typename Map>
237    GraphReader& readEdgeMap(std::string name, Map& map,
238                             const Reader& reader = Reader()) {
239      edgeset_reader.readEdgeMap(name, map, reader);
240      return *this;
241    }
242
243    template <typename Reader, typename Map>
244    GraphReader& readEdgeMap(std::string name, const Map& map,
245                             const Reader& reader = Reader()) {
246      edgeset_reader.readEdgeMap(name, map, reader);
247      return *this;
248    }
249
250    /// \brief Give a new edge map skipping command to the reader.
251    ///
252    /// Give a new edge map skipping command to the reader.
253    template <typename Reader>
254    GraphReader& skipEdgeMap(std::string name,
255                             const Reader& reader = Reader()) {
256      edgeset_reader.skipEdgeMap(name, reader);
257      return *this;
258    }
259
260    /// \brief Give a new labeled node reading command to the reader.
261    ///
262    /// Give a new labeled node reading command to the reader.
263    GraphReader& readNode(std::string name, Node& node) {
264      node_reader.readNode(name, node);
265      return *this;
266    }
267
268    /// \brief Give a new labeled edge reading command to the reader.
269    ///
270    /// Give a new labeled edge reading command to the reader.
271    GraphReader& readEdge(std::string name, Edge& edge) {
272      edge_reader.readEdge(name, edge);
273      return *this;
274    }
275
276    /// \brief Give a new attribute reading command.
277    ///
278    ///  Give a new attribute reading command.
279    template <typename Value>
280    GraphReader& readAttribute(std::string name, Value& value) {
281      attribute_reader.readAttribute(name, value);
282      return *this;
283    }
284   
285    /// \brief Give a new attribute reading command.
286    ///
287    ///  Give a new attribute reading command.
288    template <typename Reader, typename Value>
289    GraphReader& readAttribute(std::string name, Value& value,
290                               const Reader& reader) {
291      attribute_reader.readAttribute<Reader>(name, value, reader);
292      return *this;
293    }
294
295    /// \brief Conversion operator to LemonReader.
296    ///
297    /// Conversion operator to LemonReader. It makes possible to access the
298    /// encapsulated \e LemonReader, this way you can attach to this reader
299    /// new instances of \e LemonReader::SectionReader. For more details see
300    /// the \ref rwbackground "Background of Reading and Writing".
301    operator LemonReader&() {
302      return *reader;
303    }
304
305    /// \brief Executes the reading commands.
306    ///
307    /// Executes the reading commands.
308    void run() {
309      reader->run();
310    }
311
312    /// \brief Gives back the node by its id.
313    ///
314    /// It reads an id from the stream and gives back which node belongs to
315    /// it. It is possible only if there was read an "id" named node map.
316    Node readId(std::istream& is, Node) const {
317      return nodeset_reader.readId(is, Node());
318    }
319
320    /// \brief Gives back the edge by its id.
321    ///
322    /// It reads an id from the stream and gives back which edge belongs to
323    /// it. It is possible only if there was read an "id" named edge map.
324    Edge readId(std::istream& is, Edge) const {
325      return edgeset_reader.readId(is, Edge());
326    }
327
328  private:
329
330    LemonReader* reader;
331    bool own_reader;
332
333    DefaultSkipper skipper;
334
335    NodeSetReader<Graph, ReaderTraits> nodeset_reader;
336    EdgeSetReader<Graph, ReaderTraits> edgeset_reader;
337
338    NodeReader<Graph> node_reader;
339    EdgeReader<Graph> edge_reader;
340   
341    AttributeReader<ReaderTraits> attribute_reader;
342  };
343
344
345  ///\anchor readGraph()
346  ///
347  /// \brief Read a graph from an input stream.
348  ///
349  /// Read a graph from an input stream.
350  /// \param is The input stream.
351  /// \param g The graph.
352  template<typename Graph>
353  void readGraph(std::istream& is, Graph &g) {
354    GraphReader<Graph> reader(is, g);
355    reader.run();
356  }
357
358  /// \brief Read a capacitated graph instance from an input stream.
359  ///
360  /// Read a capacitated graph (graph+capacity on the
361  /// edges) from an input stream.
362  /// \param is The input stream.
363  /// \param g The graph.
364  /// \param capacity The capacity map.
365  template<typename Graph, typename CapacityMap>
366  void readGraph(std::istream& is, Graph &g, CapacityMap& capacity) {
367    GraphReader<Graph> reader(is, g);
368    reader.readEdgeMap("capacity", capacity);
369    reader.run();
370  }
371
372  /// \brief Read a shortest path instance from an input stream.
373  ///
374  /// Read a shortest path instance (graph+capacity on the
375  /// edges+designated source) from an input stream.
376  /// \param is The input stream.
377  /// \param g The graph.
378  /// \param capacity The capacity map.
379  /// \param s The source node.
380  template<typename Graph, typename CapacityMap>
381  void readGraph(std::istream& is, Graph &g, CapacityMap& capacity,
382                  typename Graph::Node &s) {
383    GraphReader<Graph> reader(is, g);
384    reader.readEdgeMap("capacity", capacity);
385    reader.readNode("source", s);
386    reader.run();
387  }
388
389
390
391  /// \brief Read a max flow instance from an input stream.
392  ///
393  /// Read a max flow instance (graph+capacity on the
394  /// edges+designated source and target) from an input stream.
395  ///
396  /// \param is The input stream.
397  /// \param g The graph.
398  /// \param capacity The capacity map.
399  /// \param s The source node.
400  /// \param t The target node.
401  template<typename Graph, typename CapacityMap>
402  void readGraph(std::istream& is, Graph &g, CapacityMap& capacity,
403                  typename Graph::Node &s, typename Graph::Node &t) {
404    GraphReader<Graph> reader(is, g);
405    reader.readEdgeMap("capacity", capacity);
406    reader.readNode("source", s);
407    reader.readNode("target", t);
408    reader.run();
409  }
410
411  /// \brief Read a min cost flow instance from an input stream.
412  ///
413  /// Read a min cost flow instance (graph+capacity on the edges+cost
414  /// function on the edges+designated source and target) from an input stream.
415  ///
416  /// \param is The input stream.
417  /// \param g The graph.
418  /// \param capacity The capacity map.
419  /// \param s The source node.
420  /// \param t The target node.
421  /// \param cost The cost map.
422  template<typename Graph, typename CapacityMap, typename CostMap>
423  void readGraph(std::istream& is, Graph &g, CapacityMap& capacity,
424                  typename Graph::Node &s, typename Graph::Node &t,
425                  CostMap& cost) {
426    GraphReader<Graph> reader(is, g);
427    reader.readEdgeMap("capacity", capacity);
428    reader.readEdgeMap("cost", cost);
429    reader.readNode("source", s);
430    reader.readNode("target", t);
431    reader.run();
432  }
433
434
435  /// \brief The undir graph reader class.
436  ///
437  /// The \c UndirGraphReader class provides the graph input.
438  /// Before you read this documentation it might be useful to read the general
439  /// description of  \ref graph-io-page "Graph Input-Output".
440  ///
441  /// If you don't need very sophisticated
442  /// behaviour then you can use the versions of the public function
443  /// \ref readGraph() to read a graph (or a max flow instance etc).
444  ///
445  /// The given file format may contain several maps and labeled nodes or
446  /// edges.
447  ///
448  /// If you read a graph you need not read all the maps and items just those
449  /// that you need. The interface of the \c UndirGraphReader is very similar
450  /// to the UndirGraphWriter but the reading method does not depend on the
451  /// order of the given commands.
452  ///
453  /// The reader object suppose that each not readed value does not contain
454  /// whitespaces, therefore it has some extra possibilities to control how
455  /// it should skip the values when the string representation contains spaces.
456  ///
457  /// \code
458  /// UndirGraphReader<UndirListGraph> reader(std::cin, graph);
459  /// \endcode
460  ///
461  /// The \c readNodeMap() function reads a map from the \c \@nodeset section.
462  /// If there is a map that you do not want to read from the file and there is
463  /// whitespace in the string represenation of the values then you should
464  /// call the \c skipNodeMap() template member function with proper
465  /// parameters.
466  ///
467  /// \code
468  /// reader.readNodeMap("coords", coords);
469  ///
470  /// reader.readNodeMap<QuotedStringReader>("label", labelMap);
471  /// reader.skipNodeMap<QuotedStringReader>("description");
472  ///
473  /// reader.readNodeMap("color", colorMap);
474  /// \endcode
475  ///
476  /// With the \c readUndirEdgeMap() member function you can give an
477  /// undir edge map reading command similar to the NodeMaps.
478  ///
479  /// \code
480  /// reader.readUndirEdgeMap("capacity", capacityMap);
481  /// \endcode
482  ///
483  /// The reading of the directed edge maps is just a syntactical sugar.
484  /// It reads two undirected edgemaps into a directed edge map. The
485  /// undirected edge maps' name should be start with the \c '+' and the
486  /// \c '-' character and the same.
487  ///
488  /// \code
489  /// reader.readEdgeMap("flow", flowMap);
490  /// \endcode
491  ///
492  /// With \c readNode() and \c readUndirEdge() functions you can read
493  /// labeled Nodes and UndirEdges.
494  ///
495  /// \code
496  /// reader.readNode("source", sourceNode);
497  /// reader.readNode("target", targetNode);
498  ///
499  /// reader.readUndirEdge("observed", undirEdge);
500  /// \endcode
501  ///
502  /// With the \c readAttribute() functions you can read an attribute
503  /// in a variable. You can specify the reader for the attribute as
504  /// the nodemaps.
505  ///
506  /// After you give all read commands you must call the \c run() member
507  /// function, which execute all the commands.
508  ///
509  /// \code
510  /// reader.run();
511  /// \endcode
512  ///
513  /// \see GraphReader
514  /// \see DefaultReaderTraits
515  /// \see \ref UndirGraphWriter
516  /// \see \ref graph-io-page
517  ///
518  /// \author Balazs Dezso
519  template <typename _Graph, typename _ReaderTraits = DefaultReaderTraits>
520  class UndirGraphReader {
521  public:
522   
523    typedef _Graph Graph;
524    typedef typename Graph::Node Node;
525    typedef typename Graph::Edge Edge;
526    typedef typename Graph::UndirEdge UndirEdge;
527
528    typedef _ReaderTraits ReaderTraits;
529    typedef typename ReaderTraits::Skipper DefaultSkipper;
530
531    /// \brief Construct a new UndirGraphReader.
532    ///
533    /// Construct a new UndirGraphReader. It reads into the given graph
534    /// and it use the given reader as the default skipper.
535    UndirGraphReader(std::istream& _is, Graph& _graph,
536                     const DefaultSkipper& _skipper = DefaultSkipper())
537      : reader(new LemonReader(_is)), own_reader(true), skipper(_skipper),
538        nodeset_reader(*reader, _graph, std::string(), skipper),
539        undir_edgeset_reader(*reader, _graph, nodeset_reader,
540                             std::string(), skipper),
541        node_reader(*reader, nodeset_reader, std::string()),
542        undir_edge_reader(*reader, undir_edgeset_reader, std::string()),
543        attribute_reader(*reader, std::string()) {}
544
545    /// \brief Construct a new UndirGraphReader.
546    ///
547    /// Construct a new UndirGraphReader. It reads into the given graph
548    /// and it use the given reader as the default skipper.
549    UndirGraphReader(const std::string& _filename, Graph& _graph,
550                     const DefaultSkipper& _skipper = DefaultSkipper())
551      : reader(new LemonReader(_filename)), own_reader(true),
552        skipper(_skipper),
553        nodeset_reader(*reader, _graph, std::string(), skipper),
554        undir_edgeset_reader(*reader, _graph, nodeset_reader,
555                             std::string(), skipper),
556        node_reader(*reader, nodeset_reader, std::string()),
557        undir_edge_reader(*reader, undir_edgeset_reader, std::string()),
558        attribute_reader(*reader, std::string()) {}
559
560    /// \brief Construct a new UndirGraphReader.
561    ///
562    /// Construct a new UndirGraphReader. It reads into the given graph
563    /// and it use the given reader as the default skipper.
564    UndirGraphReader(LemonReader& _reader, Graph& _graph,
565                     const DefaultSkipper& _skipper = DefaultSkipper())
566      : reader(_reader), own_reader(false), skipper(_skipper),
567        nodeset_reader(*reader, _graph, std::string(), skipper),
568        undir_edgeset_reader(*reader, _graph, nodeset_reader,
569                             std::string(), skipper),
570        node_reader(*reader, nodeset_reader, std::string()),
571        undir_edge_reader(*reader, undir_edgeset_reader, std::string()),
572        attribute_reader(*reader, std::string()) {}
573
574    /// \brief Destruct the graph reader.
575    ///
576    /// Destruct the graph reader.
577    ~UndirGraphReader() {
578      if (own_reader)
579        delete reader;
580    }
581
582    /// \brief Give a new node map reading command to the reader.
583    ///
584    /// Give a new node map reading command to the reader.
585    template <typename Map>
586    UndirGraphReader& readNodeMap(std::string name, Map& map) {
587      nodeset_reader.readNodeMap(name, map);
588      return *this;
589    }
590
591    template <typename Map>
592    UndirGraphReader& readNodeMap(std::string name, const Map& map) {
593      nodeset_reader.readNodeMap(name, map);
594      return *this;
595    }
596
597    /// \brief Give a new node map reading command to the reader.
598    ///
599    /// Give a new node map reading command to the reader.
600    template <typename Reader, typename Map>
601    UndirGraphReader& readNodeMap(std::string name, Map& map,
602                                  const Reader& reader = Reader()) {
603      nodeset_reader.readNodeMap(name, map, reader);
604      return *this;
605    }
606
607    template <typename Reader, typename Map>
608    UndirGraphReader& readNodeMap(std::string name, const Map& map,
609                                  const Reader& reader = Reader()) {
610      nodeset_reader.readNodeMap(name, map, reader);
611      return *this;
612    }
613
614    /// \brief Give a new node map skipping command to the reader.
615    ///
616    /// Give a new node map skipping command to the reader.
617    template <typename Reader>
618    UndirGraphReader& skipNodeMap(std::string name,
619                             const Reader& reader = Reader()) {
620      nodeset_reader.skipNodeMap(name, reader);
621      return *this;
622    }
623
624    /// \brief Give a new undirected edge map reading command to the reader.
625    ///
626    /// Give a new undirected edge map reading command to the reader.
627    template <typename Map>
628    UndirGraphReader& readUndirEdgeMap(std::string name, Map& map) {
629      undir_edgeset_reader.readUndirEdgeMap(name, map);
630      return *this;
631    }
632
633    template <typename Map>
634    UndirGraphReader& readUndirEdgeMap(std::string name, const Map& map) {
635      undir_edgeset_reader.readUndirEdgeMap(name, map);
636      return *this;
637    }
638
639
640    /// \brief Give a new undirected edge map reading command to the reader.
641    ///
642    /// Give a new undirected edge map reading command to the reader.
643    template <typename Reader, typename Map>
644    UndirGraphReader& readUndirEdgeMap(std::string name, Map& map,
645                                       const Reader& reader = Reader()) {
646      undir_edgeset_reader.readUndirEdgeMap(name, map, reader);
647      return *this;
648    }
649
650    template <typename Reader, typename Map>
651    UndirGraphReader& readUndirEdgeMap(std::string name, const Map& map,
652                                       const Reader& reader = Reader()) {
653      undir_edgeset_reader.readUndirEdgeMap(name, map, reader);
654      return *this;
655    }
656
657    /// \brief Give a new undirected edge map skipping command to the reader.
658    ///
659    /// Give a new undirected edge map skipping command to the reader.
660    template <typename Reader>
661    UndirGraphReader& skipUndirEdgeMap(std::string name,
662                                       const Reader& reader = Reader()) {
663      undir_edgeset_reader.skipUndirMap(name, reader);
664      return *this;
665    }
666
667
668    /// \brief Give a new edge map reading command to the reader.
669    ///
670    /// Give a new edge map reading command to the reader.
671    template <typename Map>
672    UndirGraphReader& readEdgeMap(std::string name, Map& map) {
673      undir_edgeset_reader.readEdgeMap(name, map);
674      return *this;
675    }
676
677    template <typename Map>
678    UndirGraphReader& readEdgeMap(std::string name, const Map& map) {
679      undir_edgeset_reader.readEdgeMap(name, map);
680      return *this;
681    }
682
683
684    /// \brief Give a new edge map reading command to the reader.
685    ///
686    /// Give a new edge map reading command to the reader.
687    template <typename Reader, typename Map>
688    UndirGraphReader& readEdgeMap(std::string name, Map& map,
689                                       const Reader& reader = Reader()) {
690      undir_edgeset_reader.readEdgeMap(name, map, reader);
691      return *this;
692    }
693
694    template <typename Reader, typename Map>
695    UndirGraphReader& readEdgeMap(std::string name, const Map& map,
696                                       const Reader& reader = Reader()) {
697      undir_edgeset_reader.readEdgeMap(name, map, reader);
698      return *this;
699    }
700
701    /// \brief Give a new edge map skipping command to the reader.
702    ///
703    /// Give a new edge map skipping command to the reader.
704    template <typename Reader>
705    UndirGraphReader& skipEdgeMap(std::string name,
706                                       const Reader& reader = Reader()) {
707      undir_edgeset_reader.skipEdgeMap(name, reader);
708      return *this;
709    }
710
711    /// \brief Give a new labeled node reading command to the reader.
712    ///
713    /// Give a new labeled node reading command to the reader.
714    UndirGraphReader& readNode(std::string name, Node& node) {
715      node_reader.readNode(name, node);
716      return *this;
717    }
718
719    /// \brief Give a new labeled edge reading command to the reader.
720    ///
721    /// Give a new labeled edge reading command to the reader.
722    UndirGraphReader& readEdge(std::string name, Edge& edge) {
723      undir_edge_reader.readEdge(name, edge);
724    }
725
726    /// \brief Give a new labeled undirected edge reading command to the
727    /// reader.
728    ///
729    /// Give a new labeled undirected edge reading command to the reader.
730    UndirGraphReader& readUndirEdge(std::string name, UndirEdge& edge) {
731      undir_edge_reader.readUndirEdge(name, edge);
732    }
733
734    /// \brief Give a new attribute reading command.
735    ///
736    ///  Give a new attribute reading command.
737    template <typename Value>
738    UndirGraphReader& readAttribute(std::string name, Value& value) {
739      attribute_reader.readAttribute(name, value);
740      return *this;
741    }
742   
743    /// \brief Give a new attribute reading command.
744    ///
745    ///  Give a new attribute reading command.
746    template <typename Reader, typename Value>
747    UndirGraphReader& readAttribute(std::string name, Value& value,
748                               const Reader& reader) {
749      attribute_reader.readAttribute<Reader>(name, value, reader);
750      return *this;
751    }
752
753    /// \brief Conversion operator to LemonReader.
754    ///
755    /// Conversion operator to LemonReader. It make possible
756    /// to access the encapsulated \e LemonReader, this way
757    /// you can attach to this reader new instances of
758    /// \e LemonReader::SectionReader.
759    operator LemonReader&() {
760      return *reader;
761    }
762
763    /// \brief Executes the reading commands.
764    ///
765    /// Executes the reading commands.
766    void run() {
767      reader->run();
768    }
769
770    /// \brief Gives back the node by its id.
771    ///
772    /// It reads an id from the stream and gives back which node belongs to
773    /// it. It is possible only if there was read an "id" named node map.
774    Node readId(std::istream& is, Node) const {
775      return nodeset_reader.readId(is, Node());
776    }
777
778    /// \brief Gives back the edge by its id.
779    ///
780    /// It reads an id from the stream and gives back which edge belongs to
781    /// it. It is possible only if there was read an "id" named edge map.
782    Edge readId(std::istream& is, Edge) const {
783      return undir_edgeset_reader.readId(is, Edge());
784    }
785
786    /// \brief Gives back the undirected edge by its id.
787    ///
788    /// It reads an id from the stream and gives back which undirected edge
789    /// belongs to it. It is possible only if there was read an "id" named
790    /// edge map.
791    UndirEdge readId(std::istream& is, UndirEdge) const {
792      return undir_edgeset_reader.readId(is, UndirEdge());
793    }
794   
795
796  private:
797
798    LemonReader* reader;
799    bool own_reader;
800
801    DefaultSkipper skipper;
802
803    NodeSetReader<Graph, ReaderTraits> nodeset_reader;
804    UndirEdgeSetReader<Graph, ReaderTraits> undir_edgeset_reader;
805
806    NodeReader<Graph> node_reader;
807    UndirEdgeReader<Graph> undir_edge_reader;
808   
809    AttributeReader<ReaderTraits> attribute_reader;
810  };
811
812  /// \brief Read an undirected graph from an input stream.
813  ///
814  /// Read an undirected graph from an input stream.
815  /// \param is The input stream.
816  /// \param g The graph.
817  template<typename Graph>
818  void readUndirGraph(std::istream& is, Graph &g) {
819    UndirGraphReader<Graph> reader(is, g);
820    reader.run();
821  }
822
823  /// \brief Read an undirected multigraph (undirected graph + capacity
824  /// map on the edges) from an input stream.
825  ///
826  /// Read an undirected multigraph (undirected graph + capacity
827  /// map on the edges) from an input stream.
828  /// \param is The input stream.
829  /// \param g The graph.
830  /// \param capacity The capacity map.
831  template<typename Graph, typename CapacityMap>
832  void readUndirGraph(std::istream& is, Graph &g, CapacityMap& capacity) {
833    UndirGraphReader<Graph> reader(is, g);
834    reader.readUndirEdgeMap("capacity", capacity);
835    reader.run();
836  }
837
838
839  /// @}
840}
841
842#endif
Note: See TracBrowser for help on using the repository browser.