Added the function isFinite(), and replaced the calls to finite() with it.
This was necessary because finite() is not a standard function. Neither can
we use its standard counterpart isfinite(), because it was introduced only
in C99, and therefore it is not supplied by all C++ implementations.
3 * This file is a part of LEMON, a generic C++ optimization library
5 * Copyright (C) 2003-2007
6 * Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport
7 * (Egervary Research Group on Combinatorial Optimization, EGRES).
9 * Permission to use, modify and distribute this software is granted
10 * provided that this copyright notice appears in all copies. For
11 * precise terms see the accompanying LICENSE file.
13 * This software is provided "AS IS" with no warranty of any kind,
14 * express or implied, and with no claim as to its suitability for any
21 ///\brief Lemon Graph Format reader.
23 #ifndef LEMON_GRAPH_READER_H
24 #define LEMON_GRAPH_READER_H
28 #include <lemon/error.h>
29 #include <lemon/lemon_reader.h>
33 /// \addtogroup lemon_io
36 /// \brief The graph reader class.
38 /// The \c GraphReader class provides the graph input.
39 /// Before you read this documentation it might be useful to read the general
40 /// description of \ref graph-io-page "Graph Input-Output".
42 /// The file to be read may contain several maps and labeled
43 /// (designated) nodes or edges.
45 /// If you read a graph you need not read all the maps and items just those
46 /// that you need. The interface of the \c GraphReader is very similar to
47 /// the GraphWriter but the reading method does not depend on the order the
48 /// given commands (i.e. you don't have to insist on the order in which the
49 /// maps are given in the file).
51 /// The reader object assumes that not read values do not contain
52 /// whitespaces, therefore it has some extra possibilities to control how
53 /// it should skip the values when the string representation contains spaces.
56 /// GraphReader<ListGraph> reader(std::cin, graph);
59 /// The \c readNodeMap() function reads a map from the \c \@nodeset section.
60 /// If there is a map that you do not want to read from the file and there is
61 /// whitespace in the string represenation of the values then you should
62 /// call the \c skipNodeMap() template member function with proper
66 /// reader.readNodeMap("coords", coords);
68 /// reader.skipNodeMap("description", desc);
70 /// reader.readNodeMap("color", colorMap);
73 /// With the \c readEdgeMap() member function you can give an edge map
74 /// reading command similar to the NodeMaps.
77 /// reader.readEdgeMap("weight", weightMap);
78 /// reader.readEdgeMap("label", labelMap);
81 /// With \c readNode() and \c readEdge() functions you can read
82 /// labeled Nodes and Edges.
85 /// reader.readNode("source", sourceNode);
86 /// reader.readNode("target", targetNode);
88 /// reader.readEdge("observed", edge);
91 /// With the \c readAttribute() functions you can read an attribute
92 /// into a variable. You can specify the reader for the attribute as
95 /// After you give all read commands you must call the \c run() member
96 /// function, which executes all the commands.
102 /// \see DefaultReaderTraits
103 /// \see QuotedStringReader
104 /// \see \ref GraphWriter
105 /// \see \ref graph-io-page
106 /// \author Balazs Dezso
107 template <typename _Graph, typename _ReaderTraits = DefaultReaderTraits>
111 typedef _Graph Graph;
112 typedef typename Graph::Node Node;
113 typedef typename Graph::Edge Edge;
115 typedef _ReaderTraits ReaderTraits;
116 typedef typename ReaderTraits::Skipper DefaultSkipper;
118 /// \brief Construct a new GraphReader.
120 /// Construct a new GraphReader. It reads into the given graph
121 /// and it uses the given reader as the default skipper.
122 GraphReader(std::istream& _is, Graph& _graph,
123 const DefaultSkipper& _skipper = DefaultSkipper())
124 : reader(new LemonReader(_is)), own_reader(true), skipper(_skipper),
125 nodeset_reader(*reader, _graph, std::string(), skipper),
126 edgeset_reader(*reader, _graph, nodeset_reader,
127 std::string(), skipper),
128 node_reader(*reader, nodeset_reader, std::string()),
129 edge_reader(*reader, edgeset_reader, std::string()),
130 attribute_reader(*reader, std::string()) {}
132 /// \brief Construct a new GraphReader.
134 /// Construct a new GraphReader. It reads into the given graph
135 /// and it uses the given reader as the default skipper.
136 GraphReader(const std::string& _filename, Graph& _graph,
137 const DefaultSkipper& _skipper = DefaultSkipper())
138 : reader(new LemonReader(_filename)), own_reader(true),
140 nodeset_reader(*reader, _graph, std::string(), skipper),
141 edgeset_reader(*reader, _graph, nodeset_reader,
142 std::string(), skipper),
143 node_reader(*reader, nodeset_reader, std::string()),
144 edge_reader(*reader, edgeset_reader, std::string()),
145 attribute_reader(*reader, std::string()) {}
147 /// \brief Construct a new GraphReader.
149 /// Construct a new GraphReader. It reads into the given graph
150 /// and it uses the given reader as the default skipper.
151 GraphReader(LemonReader& _reader, Graph& _graph,
152 const DefaultSkipper& _skipper = DefaultSkipper())
153 : reader(_reader), own_reader(false), skipper(_skipper),
154 nodeset_reader(*reader, _graph, std::string(), skipper),
155 edgeset_reader(*reader, _graph, nodeset_reader,
156 std::string(), skipper),
157 node_reader(*reader, nodeset_reader, std::string()),
158 edge_reader(*reader, edgeset_reader, std::string()),
159 attribute_reader(*reader, std::string()) {}
161 /// \brief Destruct the graph reader.
163 /// Destruct the graph reader.
169 /// \brief Give a new node map reading command to the reader.
171 /// Give a new node map reading command to the reader.
172 template <typename Map>
173 GraphReader& readNodeMap(std::string name, Map& map) {
174 nodeset_reader.readNodeMap(name, map);
178 template <typename Map>
179 GraphReader& readNodeMap(std::string name, const Map& map) {
180 nodeset_reader.readNodeMap(name, map);
184 /// \brief Give a new node map reading command to the reader.
186 /// Give a new node map reading command to the reader.
187 template <typename ItemReader, typename Map>
188 GraphReader& readNodeMap(std::string name, Map& map,
189 const ItemReader& ir = ItemReader()) {
190 nodeset_reader.readNodeMap(name, map, ir);
194 template <typename ItemReader, typename Map>
195 GraphReader& readNodeMap(std::string name, const Map& map,
196 const ItemReader& ir = ItemReader()) {
197 nodeset_reader.readNodeMap(name, map, ir);
201 /// \brief Give a new node map skipping command to the reader.
203 /// Give a new node map skipping command to the reader.
204 template <typename ItemReader>
205 GraphReader& skipNodeMap(std::string name,
206 const ItemReader& ir = ItemReader()) {
207 nodeset_reader.skipNodeMap(name, ir);
211 /// \brief Give a new edge map reading command to the reader.
213 /// Give a new edge map reading command to the reader.
214 template <typename Map>
215 GraphReader& readEdgeMap(std::string name, Map& map) {
216 edgeset_reader.readEdgeMap(name, map);
220 template <typename Map>
221 GraphReader& readEdgeMap(std::string name, const Map& map) {
222 edgeset_reader.readEdgeMap(name, map);
227 /// \brief Give a new edge map reading command to the reader.
229 /// Give a new edge map reading command to the reader.
230 template <typename ItemReader, typename Map>
231 GraphReader& readEdgeMap(std::string name, Map& map,
232 const ItemReader& ir = ItemReader()) {
233 edgeset_reader.readEdgeMap(name, map, ir);
237 template <typename ItemReader, typename Map>
238 GraphReader& readEdgeMap(std::string name, const Map& map,
239 const ItemReader& ir = ItemReader()) {
240 edgeset_reader.readEdgeMap(name, map, ir);
244 /// \brief Give a new edge map skipping command to the reader.
246 /// Give a new edge map skipping command to the reader.
247 template <typename ItemReader>
248 GraphReader& skipEdgeMap(std::string name,
249 const ItemReader& ir = ItemReader()) {
250 edgeset_reader.skipEdgeMap(name, ir);
254 /// \brief Give a new labeled node reading command to the reader.
256 /// Give a new labeled node reading command to the reader.
257 GraphReader& readNode(std::string name, Node& node) {
258 node_reader.readNode(name, node);
262 /// \brief Give a new labeled edge reading command to the reader.
264 /// Give a new labeled edge reading command to the reader.
265 GraphReader& readEdge(std::string name, Edge& edge) {
266 edge_reader.readEdge(name, edge);
270 /// \brief Give a new attribute reading command.
272 /// Give a new attribute reading command.
273 template <typename Value>
274 GraphReader& readAttribute(std::string name, Value& value) {
275 attribute_reader.readAttribute(name, value);
279 /// \brief Give a new attribute reading command.
281 /// Give a new attribute reading command.
282 template <typename ItemReader, typename Value>
283 GraphReader& readAttribute(std::string name, Value& value,
284 const ItemReader& ir = ItemReader()) {
285 attribute_reader.readAttribute(name, value, ir);
289 /// \brief Conversion operator to LemonReader.
291 /// Conversion operator to LemonReader. It makes possible to access the
292 /// encapsulated \e LemonReader, this way you can attach to this reader
293 /// new instances of \e LemonReader::SectionReader. For more details see
294 /// the \ref rwbackground "Background of Reading and Writing".
295 operator LemonReader&() {
299 /// \brief Executes the reading commands.
301 /// Executes the reading commands.
307 /// \brief Returns true if the reader can give back the items by its label.
309 /// \brief Returns true if the reader can give back the items by its label.
310 bool isLabelReader() const {
311 return nodeset_reader.isLabelReader() && edgeset_reader.isLabelReader();
314 /// \brief Gives back the node by its label.
316 /// It reads an label from the stream and gives back which node belongs to
317 /// it. It is possible only if there was read a "label" named node map.
318 void readLabel(std::istream& is, Node& node) const {
319 nodeset_reader.readLabel(is, node);
322 /// \brief Gives back the edge by its label.
324 /// It reads an label from the stream and gives back which edge belongs to
325 /// it. It is possible only if there was read a "label" named edge map.
326 void readLabel(std::istream& is, Edge& edge) const {
327 edgeset_reader.readLabel(is, edge);
335 DefaultSkipper skipper;
337 NodeSetReader<Graph, ReaderTraits> nodeset_reader;
338 EdgeSetReader<Graph, ReaderTraits> edgeset_reader;
340 NodeReader<Graph> node_reader;
341 EdgeReader<Graph> edge_reader;
343 AttributeReader<ReaderTraits> attribute_reader;
347 /// \brief The undirected graph reader class.
349 /// The \c UGraphReader class provides the graph input.
350 /// Before you read this documentation it might be useful to read the general
351 /// description of \ref graph-io-page "Graph Input-Output".
353 /// The given file format may contain several maps and labeled nodes or
356 /// If you read a graph you need not read all the maps and items just those
357 /// that you need. The interface of the \c UGraphReader is very similar
358 /// to the UGraphWriter but the reading method does not depend on the
359 /// order of the given commands.
361 /// The reader object suppose that each not read value does not contain
362 /// whitespaces, therefore it has some extra possibilities to control how
363 /// it should skip the values when the string representation contains spaces.
366 /// UGraphReader<ListUGraph> reader(std::cin, graph);
369 /// The \c readNodeMap() function reads a map from the \c \@nodeset section.
370 /// If there is a map that you do not want to read from the file and there is
371 /// whitespace in the string represenation of the values then you should
372 /// call the \c skipNodeMap() template member function with proper
376 /// reader.readNodeMap("coords", coords);
378 /// reader.skipNodeMap("description", desc);
380 /// reader.readNodeMap("color", colorMap);
383 /// With the \c readUEdgeMap() member function you can give an
384 /// uedge map reading command similar to the NodeMaps.
387 /// reader.readUEdgeMap("capacity", capacityMap);
390 /// The reading of the directed edge maps is just a syntactical sugar.
391 /// It reads two undirected edgemaps into a directed edge map. The
392 /// undirected edge maps' name should be start with the \c '+' and the
393 /// \c '-' character and the same.
396 /// reader.readEdgeMap("flow", flowMap);
399 /// With \c readNode() and \c readUEdge() functions you can read
400 /// labeled Nodes and UEdges.
403 /// reader.readNode("source", sourceNode);
404 /// reader.readNode("target", targetNode);
406 /// reader.readUEdge("observed", uEdge);
409 /// With the \c readAttribute() functions you can read an attribute
410 /// in a variable. You can specify the reader for the attribute as
413 /// After you give all read commands you must call the \c run() member
414 /// function, which execute all the commands.
421 /// \see DefaultReaderTraits
422 /// \see \ref UGraphWriter
423 /// \see \ref graph-io-page
425 /// \author Balazs Dezso
426 template <typename _Graph, typename _ReaderTraits = DefaultReaderTraits>
430 typedef _Graph Graph;
431 typedef typename Graph::Node Node;
432 typedef typename Graph::Edge Edge;
433 typedef typename Graph::UEdge UEdge;
435 typedef _ReaderTraits ReaderTraits;
436 typedef typename ReaderTraits::Skipper DefaultSkipper;
438 /// \brief Construct a new UGraphReader.
440 /// Construct a new UGraphReader. It reads into the given graph
441 /// and it use the given reader as the default skipper.
442 UGraphReader(std::istream& _is, Graph& _graph,
443 const DefaultSkipper& _skipper = DefaultSkipper())
444 : reader(new LemonReader(_is)), own_reader(true), skipper(_skipper),
445 nodeset_reader(*reader, _graph, std::string(), skipper),
446 uedgeset_reader(*reader, _graph, nodeset_reader,
447 std::string(), skipper),
448 node_reader(*reader, nodeset_reader, std::string()),
449 uedge_reader(*reader, uedgeset_reader, std::string()),
450 attribute_reader(*reader, std::string()) {}
452 /// \brief Construct a new UGraphReader.
454 /// Construct a new UGraphReader. It reads into the given graph
455 /// and it use the given reader as the default skipper.
456 UGraphReader(const std::string& _filename, Graph& _graph,
457 const DefaultSkipper& _skipper = DefaultSkipper())
458 : reader(new LemonReader(_filename)), own_reader(true),
460 nodeset_reader(*reader, _graph, std::string(), skipper),
461 uedgeset_reader(*reader, _graph, nodeset_reader,
462 std::string(), skipper),
463 node_reader(*reader, nodeset_reader, std::string()),
464 uedge_reader(*reader, uedgeset_reader, std::string()),
465 attribute_reader(*reader, std::string()) {}
467 /// \brief Construct a new UGraphReader.
469 /// Construct a new UGraphReader. It reads into the given graph
470 /// and it use the given reader as the default skipper.
471 UGraphReader(LemonReader& _reader, Graph& _graph,
472 const DefaultSkipper& _skipper = DefaultSkipper())
473 : reader(_reader), own_reader(false), skipper(_skipper),
474 nodeset_reader(*reader, _graph, std::string(), skipper),
475 uedgeset_reader(*reader, _graph, nodeset_reader,
476 std::string(), skipper),
477 node_reader(*reader, nodeset_reader, std::string()),
478 uedge_reader(*reader, uedgeset_reader, std::string()),
479 attribute_reader(*reader, std::string()) {}
481 /// \brief Destruct the graph reader.
483 /// Destruct the graph reader.
489 /// \brief Give a new node map reading command to the reader.
491 /// Give a new node map reading command to the reader.
492 template <typename Map>
493 UGraphReader& readNodeMap(std::string name, Map& map) {
494 nodeset_reader.readNodeMap(name, map);
498 template <typename Map>
499 UGraphReader& readNodeMap(std::string name, const Map& map) {
500 nodeset_reader.readNodeMap(name, map);
504 /// \brief Give a new node map reading command to the reader.
506 /// Give a new node map reading command to the reader.
507 template <typename ItemReader, typename Map>
508 UGraphReader& readNodeMap(std::string name, Map& map,
509 const ItemReader& ir = ItemReader()) {
510 nodeset_reader.readNodeMap(name, map, ir);
514 template <typename ItemReader, typename Map>
515 UGraphReader& readNodeMap(std::string name, const Map& map,
516 const ItemReader& ir = ItemReader()) {
517 nodeset_reader.readNodeMap(name, map, ir);
521 /// \brief Give a new node map skipping command to the reader.
523 /// Give a new node map skipping command to the reader.
524 template <typename ItemReader>
525 UGraphReader& skipNodeMap(std::string name,
526 const ItemReader& ir = ItemReader()) {
527 nodeset_reader.skipNodeMap(name, ir);
531 /// \brief Give a new undirected edge map reading command to the reader.
533 /// Give a new undirected edge map reading command to the reader.
534 template <typename Map>
535 UGraphReader& readUEdgeMap(std::string name, Map& map) {
536 uedgeset_reader.readUEdgeMap(name, map);
540 template <typename Map>
541 UGraphReader& readUEdgeMap(std::string name, const Map& map) {
542 uedgeset_reader.readUEdgeMap(name, map);
547 /// \brief Give a new undirected edge map reading command to the reader.
549 /// Give a new undirected edge map reading command to the reader.
550 template <typename ItemReader, typename Map>
551 UGraphReader& readUEdgeMap(std::string name, Map& map,
552 const ItemReader& ir = ItemReader()) {
553 uedgeset_reader.readUEdgeMap(name, map, ir);
557 template <typename ItemReader, typename Map>
558 UGraphReader& readUEdgeMap(std::string name, const Map& map,
559 const ItemReader& ir = ItemReader()) {
560 uedgeset_reader.readUEdgeMap(name, map, ir);
564 /// \brief Give a new undirected edge map skipping command to the reader.
566 /// Give a new undirected edge map skipping command to the reader.
567 template <typename ItemReader>
568 UGraphReader& skipUEdgeMap(std::string name,
569 const ItemReader& ir = ItemReader()) {
570 uedgeset_reader.skipUMap(name, ir);
575 /// \brief Give a new edge map reading command to the reader.
577 /// Give a new edge map reading command to the reader.
578 template <typename Map>
579 UGraphReader& readEdgeMap(std::string name, Map& map) {
580 uedgeset_reader.readEdgeMap(name, map);
584 template <typename Map>
585 UGraphReader& readEdgeMap(std::string name, const Map& map) {
586 uedgeset_reader.readEdgeMap(name, map);
591 /// \brief Give a new edge map reading command to the reader.
593 /// Give a new edge map reading command to the reader.
594 template <typename ItemReader, typename Map>
595 UGraphReader& readEdgeMap(std::string name, Map& map,
596 const ItemReader& ir = ItemReader()) {
597 uedgeset_reader.readEdgeMap(name, map, ir);
601 template <typename ItemReader, typename Map>
602 UGraphReader& readEdgeMap(std::string name, const Map& map,
603 const ItemReader& ir = ItemReader()) {
604 uedgeset_reader.readEdgeMap(name, map, ir);
608 /// \brief Give a new edge map skipping command to the reader.
610 /// Give a new edge map skipping command to the reader.
611 template <typename ItemReader>
612 UGraphReader& skipEdgeMap(std::string name,
613 const ItemReader& ir = ItemReader()) {
614 uedgeset_reader.skipEdgeMap(name, ir);
618 /// \brief Give a new labeled node reading command to the reader.
620 /// Give a new labeled node reading command to the reader.
621 UGraphReader& readNode(std::string name, Node& node) {
622 node_reader.readNode(name, node);
626 /// \brief Give a new labeled edge reading command to the reader.
628 /// Give a new labeled edge reading command to the reader.
629 UGraphReader& readEdge(std::string name, Edge& edge) {
630 uedge_reader.readEdge(name, edge);
633 /// \brief Give a new labeled undirected edge reading command to the
636 /// Give a new labeled undirected edge reading command to the reader.
637 UGraphReader& readUEdge(std::string name, UEdge& edge) {
638 uedge_reader.readUEdge(name, edge);
641 /// \brief Give a new attribute reading command.
643 /// Give a new attribute reading command.
644 template <typename Value>
645 UGraphReader& readAttribute(std::string name, Value& value) {
646 attribute_reader.readAttribute(name, value);
650 /// \brief Give a new attribute reading command.
652 /// Give a new attribute reading command.
653 template <typename ItemReader, typename Value>
654 UGraphReader& readAttribute(std::string name, Value& value,
655 const ItemReader& ir = ItemReader()) {
656 attribute_reader.readAttribute(name, value, ir);
660 /// \brief Conversion operator to LemonReader.
662 /// Conversion operator to LemonReader. It make possible
663 /// to access the encapsulated \e LemonReader, this way
664 /// you can attach to this reader new instances of
665 /// \e LemonReader::SectionReader.
666 operator LemonReader&() {
670 /// \brief Executes the reading commands.
672 /// Executes the reading commands.
678 /// \brief Returns true if the reader can give back the items by its label.
680 /// Returns true if the reader can give back the items by its label.
681 bool isLabelReader() const {
682 return nodeset_reader.isLabelReader() &&
683 uedgeset_reader.isLabelReader();
686 /// \brief Gives back the node by its label.
688 /// It reads an label from the stream and gives back which node belongs to
689 /// it. It is possible only if there was read a "label" named node map.
690 void readLabel(std::istream& is, Node& node) const {
691 return nodeset_reader.readLabel(is, node);
694 /// \brief Gives back the edge by its label
696 /// It reads an label from the stream and gives back which edge belongs to
697 /// it. It is possible only if there was read a "label" named edge map.
698 void readLabel(std::istream& is, Edge& edge) const {
699 return uedgeset_reader.readLabel(is, edge);
702 /// \brief Gives back the undirected edge by its label.
704 /// It reads an label from the stream and gives back which undirected edge
705 /// belongs to it. It is possible only if there was read a "label" named
707 void readLabel(std::istream& is, UEdge& uedge) const {
708 return uedgeset_reader.readLabel(is, uedge);
717 DefaultSkipper skipper;
719 NodeSetReader<Graph, ReaderTraits> nodeset_reader;
720 UEdgeSetReader<Graph, ReaderTraits> uedgeset_reader;
722 NodeReader<Graph> node_reader;
723 UEdgeReader<Graph> uedge_reader;
725 AttributeReader<ReaderTraits> attribute_reader;