2 * src/lemon/graph_writer.h - Part of LEMON, a generic C++ optimization library
4 * Copyright (C) 2004 Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport
5 * (Egervary Combinatorial Optimization Research Group, EGRES).
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.
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
19 ///\brief Graph writer.
30 #include <lemon/invalid.h>
31 #include <lemon/error.h>
36 struct DefaultWriterTraits {
38 template <typename _Value>
42 void write(std::ostream& os, const Value& value) {
50 class QuotedStringWriter {
52 typedef std::string Value;
54 QuotedStringWriter(bool _escaped = true) : escaped(_escaped) {}
56 void write(std::ostream& os, const std::string& value) {
60 for (int i = 0; i < (int)value.size(); ++i) {
61 writeEscape(ls, value[i]);
72 static void writeEscape(std::ostream& os, char c) {
109 os << '\\' << oct << (int)c;
122 template <typename _Graph, typename _WriterTraits = DefaultWriterTraits>
126 typedef _Graph Graph;
127 typedef typename Graph::Node Node;
128 typedef typename Graph::NodeIt NodeIt;
129 typedef typename Graph::Edge Edge;
130 typedef typename Graph::EdgeIt EdgeIt;
132 typedef _WriterTraits WriterTraits;
134 GraphWriter(std::ostream& _os, Graph& _graph) : os(_os), graph(_graph) {}
138 for (typename NodeMapWriters::iterator it = node_map_writers.begin();
139 it != node_map_writers.end(); ++it) {
143 for (typename EdgeMapWriters::iterator it = edge_map_writers.begin();
144 it != edge_map_writers.end(); ++it) {
152 template <typename Map>
153 GraphWriter& addNodeMap(std::string name, const Map& map) {
154 return addNodeMap<typename WriterTraits::template Writer<
155 typename Map::Value>, Map>(name, map);
158 template <typename Writer, typename Map>
159 GraphWriter& addNodeMap(std::string name, const Map& map,
160 const Writer& writer = Writer()) {
161 // if (node_map_writers.find(name) != node_map_writers.end()) {
162 // throw Exception() << "Multiple write rule for node map: "
165 node_map_writers.push_back(
166 make_pair(name, new MapWriter<Node, Map, Writer>(map, writer)));
172 template <typename Map>
173 GraphWriter& addEdgeMap(std::string name, const Map& map) {
174 return addEdgeMap<typename WriterTraits::template Writer<typename Map::Value>, Map>(name, map);
178 template <typename Writer, typename Map>
179 GraphWriter& addEdgeMap(std::string name, const Map& map, const Writer& writer = Writer()) {
180 // if (edge_map_writers.find(name) != edge_map_writers.end()) {
181 // throw Exception() << "Multiple write rule for edge map: " << name;
183 edge_map_writers.push_back(make_pair(name, new MapWriter<Edge, Map, Writer>(map, writer)));
188 GraphWriter& addNode(std::string name, const Node& node) {
189 // if (node_writers.find(name) != node_writers.end()) {
190 // throw Exception() << "Multiple write rule for node";
192 node_writers.push_back(make_pair(name, node));
198 GraphWriter& addEdge(std::string name, const Edge& edge) {
199 // if (edge_writers.find(name) != edge_writers.end()) {
200 // throw Exception() << "Multiple write rule for edge";
202 edge_writers.push_back(make_pair(name, edge));
211 os << "@end" << std::endl;
216 void writeNodeSet() {
217 if (node_map_writers.size() == 0) return;
218 os << "@nodeset" << std::endl;
219 for (int i = 0; i < (int)node_map_writers.size(); ++i) {
220 os << node_map_writers[i].first << '\t';
223 for (NodeIt it(graph); it != INVALID; ++it) {
224 for (int i = 0; i < (int)node_map_writers.size(); ++i) {
225 node_map_writers[i].second->write(os, it);
232 void writeEdgeSet() {
233 if (edge_map_writers.size() == 0) return;
234 if (node_map_writers.size() == 0) {
235 throw Exception() << "Missing node id map";
237 os << "@edgeset" << std::endl;
239 for (int i = 0; i < (int)edge_map_writers.size(); ++i) {
240 os << edge_map_writers[i].first << '\t';
243 for (EdgeIt it(graph); it != INVALID; ++it) {
244 node_map_writers[0].second->write(os, graph.source(it));
245 node_map_writers[0].second->write(os, graph.target(it));
246 for (int i = 0; i < (int)edge_map_writers.size(); ++i) {
247 edge_map_writers[i].second->write(os, it);
254 if (node_writers.size() == 0) return;
255 if (node_map_writers.size() == 0) {
256 throw Exception() << "Missing node id map";
258 os << "@nodes" << std::endl;
259 for (int i = 0; i < (int)node_writers.size(); ++i) {
260 os << node_writers[i].first << '\t';
261 node_map_writers[0].second->write(os, node_writers[i].second);
267 if (edge_writers.size() == 0) return;
268 if (edge_map_writers.size() == 0) {
269 throw Exception() << "Missing edge id map";
271 os << "@edges" << std::endl;
272 for (int i = 0; i < (int)edge_writers.size(); ++i) {
273 os << edge_writers[i].first << '\t';
274 edge_map_writers[0].second->write(os, edge_writers[i].second);
281 template <class _Item>
285 virtual void write(std::ostream&, const Item&) = 0;
288 template <class _Item, typename _Map, typename _Writer>
289 class MapWriter : public WriterBase<_Item> {
292 typedef _Writer Writer;
293 typedef typename Writer::Value Value;
299 MapWriter(const Map& _map, const Writer& _writer)
300 : map(_map), writer(_writer) {}
303 virtual void write(std::ostream& os, const Item& item) {
304 writer.write(os, map[item]);
311 typedef std::vector< std::pair<std::string, WriterBase<Node>*> >
313 NodeMapWriters node_map_writers;
315 typedef std::vector< std::pair<std::string, WriterBase<Edge>*> >
317 EdgeMapWriters edge_map_writers;
319 typedef std::vector<std::pair<std::string, Node> > NodeWriters;
320 NodeWriters node_writers;
322 typedef std::vector<std::pair<std::string, Edge> > EdgeWriters;
323 EdgeWriters edge_writers;