1.1 --- a/lemon/lgf_reader.h Sun Feb 05 00:04:44 2012 +0100
1.2 +++ b/lemon/lgf_reader.h Tue Feb 12 07:15:52 2013 +0100
1.3 @@ -154,16 +154,16 @@
1.4 }
1.5 };
1.6
1.7 - template <typename Value>
1.8 + template <typename Value,
1.9 + typename Map = std::map<std::string, Value> >
1.10 struct MapLookUpConverter {
1.11 - const std::map<std::string, Value>& _map;
1.12 -
1.13 - MapLookUpConverter(const std::map<std::string, Value>& map)
1.14 + const Map& _map;
1.15 +
1.16 + MapLookUpConverter(const Map& map)
1.17 : _map(map) {}
1.18
1.19 Value operator()(const std::string& str) {
1.20 - typename std::map<std::string, Value>::const_iterator it =
1.21 - _map.find(str);
1.22 + typename Map::const_iterator it = _map.find(str);
1.23 if (it == _map.end()) {
1.24 std::ostringstream msg;
1.25 msg << "Item not found: " << str;
1.26 @@ -173,6 +173,39 @@
1.27 }
1.28 };
1.29
1.30 + template <typename Value,
1.31 + typename Map1 = std::map<std::string, Value>,
1.32 + typename Map2 = std::map<std::string, Value> >
1.33 + struct DoubleMapLookUpConverter {
1.34 + const Map1& _map1;
1.35 + const Map2& _map2;
1.36 +
1.37 + DoubleMapLookUpConverter(const Map1& map1, const Map2& map2)
1.38 + : _map1(map1), _map2(map2) {}
1.39 +
1.40 + Value operator()(const std::string& str) {
1.41 + typename Map1::const_iterator it1 = _map1.find(str);
1.42 + typename Map2::const_iterator it2 = _map2.find(str);
1.43 + if (it1 == _map1.end()) {
1.44 + if (it2 == _map2.end()) {
1.45 + std::ostringstream msg;
1.46 + msg << "Item not found: " << str;
1.47 + throw FormatError(msg.str());
1.48 + } else {
1.49 + return it2->second;
1.50 + }
1.51 + } else {
1.52 + if (it2 == _map2.end()) {
1.53 + return it1->second;
1.54 + } else {
1.55 + std::ostringstream msg;
1.56 + msg << "Item is ambigous: " << str;
1.57 + throw FormatError(msg.str());
1.58 + }
1.59 + }
1.60 + }
1.61 + };
1.62 +
1.63 template <typename GR>
1.64 struct GraphArcLookUpConverter {
1.65 const GR& _graph;
1.66 @@ -2171,15 +2204,19 @@
1.67 std::string _edges_caption;
1.68 std::string _attributes_caption;
1.69
1.70 - typedef std::map<std::string, Node> NodeIndex;
1.71 - NodeIndex _node_index;
1.72 + typedef std::map<std::string, RedNode> RedNodeIndex;
1.73 + RedNodeIndex _red_node_index;
1.74 + typedef std::map<std::string, BlueNode> BlueNodeIndex;
1.75 + BlueNodeIndex _blue_node_index;
1.76 typedef std::map<std::string, Edge> EdgeIndex;
1.77 EdgeIndex _edge_index;
1.78
1.79 typedef std::vector<std::pair<std::string,
1.80 - _reader_bits::MapStorageBase<Node>*> > NodeMaps;
1.81 - NodeMaps _red_maps;
1.82 - NodeMaps _blue_maps;
1.83 + _reader_bits::MapStorageBase<RedNode>*> > RedNodeMaps;
1.84 + RedNodeMaps _red_node_maps;
1.85 + typedef std::vector<std::pair<std::string,
1.86 + _reader_bits::MapStorageBase<BlueNode>*> > BlueNodeMaps;
1.87 + BlueNodeMaps _blue_node_maps;
1.88
1.89 typedef std::vector<std::pair<std::string,
1.90 _reader_bits::MapStorageBase<Edge>*> > EdgeMaps;
1.91 @@ -2241,13 +2278,13 @@
1.92
1.93 /// \brief Destructor
1.94 ~BpGraphReader() {
1.95 - for (typename NodeMaps::iterator it = _red_maps.begin();
1.96 - it != _red_maps.end(); ++it) {
1.97 + for (typename RedNodeMaps::iterator it = _red_node_maps.begin();
1.98 + it != _red_node_maps.end(); ++it) {
1.99 delete it->second;
1.100 }
1.101
1.102 - for (typename NodeMaps::iterator it = _blue_maps.begin();
1.103 - it != _blue_maps.end(); ++it) {
1.104 + for (typename BlueNodeMaps::iterator it = _blue_node_maps.begin();
1.105 + it != _blue_node_maps.end(); ++it) {
1.106 delete it->second;
1.107 }
1.108
1.109 @@ -2284,11 +2321,12 @@
1.110 other._is = 0;
1.111 other.local_is = false;
1.112
1.113 - _node_index.swap(other._node_index);
1.114 + _red_node_index.swap(other._red_node_index);
1.115 + _blue_node_index.swap(other._blue_node_index);
1.116 _edge_index.swap(other._edge_index);
1.117
1.118 - _red_maps.swap(other._red_maps);
1.119 - _blue_maps.swap(other._blue_maps);
1.120 + _red_node_maps.swap(other._red_node_maps);
1.121 + _blue_node_maps.swap(other._blue_node_maps);
1.122 _edge_maps.swap(other._edge_maps);
1.123 _attributes.swap(other._attributes);
1.124
1.125 @@ -2311,12 +2349,12 @@
1.126 template <typename Map>
1.127 BpGraphReader& nodeMap(const std::string& caption, Map& map) {
1.128 checkConcept<concepts::WriteMap<Node, typename Map::Value>, Map>();
1.129 - _reader_bits::MapStorageBase<Node>* red_storage =
1.130 - new _reader_bits::MapStorage<Node, Map>(map);
1.131 - _red_maps.push_back(std::make_pair(caption, red_storage));
1.132 - _reader_bits::MapStorageBase<Node>* blue_storage =
1.133 - new _reader_bits::MapStorage<Node, Map>(map);
1.134 - _blue_maps.push_back(std::make_pair(caption, blue_storage));
1.135 + _reader_bits::MapStorageBase<RedNode>* red_storage =
1.136 + new _reader_bits::MapStorage<RedNode, Map>(map);
1.137 + _red_node_maps.push_back(std::make_pair(caption, red_storage));
1.138 + _reader_bits::MapStorageBase<BlueNode>* blue_storage =
1.139 + new _reader_bits::MapStorage<BlueNode, Map>(map);
1.140 + _blue_node_maps.push_back(std::make_pair(caption, blue_storage));
1.141 return *this;
1.142 }
1.143
1.144 @@ -2328,22 +2366,22 @@
1.145 BpGraphReader& nodeMap(const std::string& caption, Map& map,
1.146 const Converter& converter = Converter()) {
1.147 checkConcept<concepts::WriteMap<Node, typename Map::Value>, Map>();
1.148 - _reader_bits::MapStorageBase<Node>* red_storage =
1.149 - new _reader_bits::MapStorage<Node, Map, Converter>(map, converter);
1.150 - _red_maps.push_back(std::make_pair(caption, red_storage));
1.151 - _reader_bits::MapStorageBase<Node>* blue_storage =
1.152 - new _reader_bits::MapStorage<Node, Map, Converter>(map, converter);
1.153 - _blue_maps.push_back(std::make_pair(caption, blue_storage));
1.154 + _reader_bits::MapStorageBase<RedNode>* red_storage =
1.155 + new _reader_bits::MapStorage<RedNode, Map, Converter>(map, converter);
1.156 + _red_node_maps.push_back(std::make_pair(caption, red_storage));
1.157 + _reader_bits::MapStorageBase<BlueNode>* blue_storage =
1.158 + new _reader_bits::MapStorage<BlueNode, Map, Converter>(map, converter);
1.159 + _blue_node_maps.push_back(std::make_pair(caption, blue_storage));
1.160 return *this;
1.161 }
1.162
1.163 /// Add a red node map reading rule to the reader.
1.164 template <typename Map>
1.165 BpGraphReader& redNodeMap(const std::string& caption, Map& map) {
1.166 - checkConcept<concepts::WriteMap<Node, typename Map::Value>, Map>();
1.167 - _reader_bits::MapStorageBase<Node>* storage =
1.168 - new _reader_bits::MapStorage<Node, Map>(map);
1.169 - _red_maps.push_back(std::make_pair(caption, storage));
1.170 + checkConcept<concepts::WriteMap<RedNode, typename Map::Value>, Map>();
1.171 + _reader_bits::MapStorageBase<RedNode>* storage =
1.172 + new _reader_bits::MapStorage<RedNode, Map>(map);
1.173 + _red_node_maps.push_back(std::make_pair(caption, storage));
1.174 return *this;
1.175 }
1.176
1.177 @@ -2354,20 +2392,20 @@
1.178 template <typename Map, typename Converter>
1.179 BpGraphReader& redNodeMap(const std::string& caption, Map& map,
1.180 const Converter& converter = Converter()) {
1.181 - checkConcept<concepts::WriteMap<Node, typename Map::Value>, Map>();
1.182 - _reader_bits::MapStorageBase<Node>* storage =
1.183 - new _reader_bits::MapStorage<Node, Map, Converter>(map, converter);
1.184 - _red_maps.push_back(std::make_pair(caption, storage));
1.185 + checkConcept<concepts::WriteMap<RedNode, typename Map::Value>, Map>();
1.186 + _reader_bits::MapStorageBase<RedNode>* storage =
1.187 + new _reader_bits::MapStorage<RedNode, Map, Converter>(map, converter);
1.188 + _red_node_maps.push_back(std::make_pair(caption, storage));
1.189 return *this;
1.190 }
1.191
1.192 /// Add a blue node map reading rule to the reader.
1.193 template <typename Map>
1.194 BpGraphReader& blueNodeMap(const std::string& caption, Map& map) {
1.195 - checkConcept<concepts::WriteMap<Node, typename Map::Value>, Map>();
1.196 - _reader_bits::MapStorageBase<Node>* storage =
1.197 - new _reader_bits::MapStorage<Node, Map>(map);
1.198 - _blue_maps.push_back(std::make_pair(caption, storage));
1.199 + checkConcept<concepts::WriteMap<BlueNode, typename Map::Value>, Map>();
1.200 + _reader_bits::MapStorageBase<BlueNode>* storage =
1.201 + new _reader_bits::MapStorage<BlueNode, Map>(map);
1.202 + _blue_node_maps.push_back(std::make_pair(caption, storage));
1.203 return *this;
1.204 }
1.205
1.206 @@ -2378,10 +2416,10 @@
1.207 template <typename Map, typename Converter>
1.208 BpGraphReader& blueNodeMap(const std::string& caption, Map& map,
1.209 const Converter& converter = Converter()) {
1.210 - checkConcept<concepts::WriteMap<Node, typename Map::Value>, Map>();
1.211 - _reader_bits::MapStorageBase<Node>* storage =
1.212 - new _reader_bits::MapStorage<Node, Map, Converter>(map, converter);
1.213 - _blue_maps.push_back(std::make_pair(caption, storage));
1.214 + checkConcept<concepts::WriteMap<BlueNode, typename Map::Value>, Map>();
1.215 + _reader_bits::MapStorageBase<BlueNode>* storage =
1.216 + new _reader_bits::MapStorage<BlueNode, Map, Converter>(map, converter);
1.217 + _blue_node_maps.push_back(std::make_pair(caption, storage));
1.218 return *this;
1.219 }
1.220
1.221 @@ -2473,14 +2511,39 @@
1.222 ///
1.223 /// Add a node reading rule to reader.
1.224 BpGraphReader& node(const std::string& caption, Node& node) {
1.225 - typedef _reader_bits::MapLookUpConverter<Node> Converter;
1.226 - Converter converter(_node_index);
1.227 + typedef _reader_bits::DoubleMapLookUpConverter<
1.228 + Node, RedNodeIndex, BlueNodeIndex> Converter;
1.229 + Converter converter(_red_node_index, _blue_node_index);
1.230 _reader_bits::ValueStorageBase* storage =
1.231 new _reader_bits::ValueStorage<Node, Converter>(node, converter);
1.232 _attributes.insert(std::make_pair(caption, storage));
1.233 return *this;
1.234 }
1.235
1.236 + /// \brief Red node reading rule
1.237 + ///
1.238 + /// Add a red node reading rule to reader.
1.239 + BpGraphReader& redNode(const std::string& caption, RedNode& node) {
1.240 + typedef _reader_bits::MapLookUpConverter<RedNode> Converter;
1.241 + Converter converter(_red_node_index);
1.242 + _reader_bits::ValueStorageBase* storage =
1.243 + new _reader_bits::ValueStorage<RedNode, Converter>(node, converter);
1.244 + _attributes.insert(std::make_pair(caption, storage));
1.245 + return *this;
1.246 + }
1.247 +
1.248 + /// \brief Blue node reading rule
1.249 + ///
1.250 + /// Add a blue node reading rule to reader.
1.251 + BpGraphReader& blueNode(const std::string& caption, BlueNode& node) {
1.252 + typedef _reader_bits::MapLookUpConverter<BlueNode> Converter;
1.253 + Converter converter(_blue_node_index);
1.254 + _reader_bits::ValueStorageBase* storage =
1.255 + new _reader_bits::ValueStorage<BlueNode, Converter>(node, converter);
1.256 + _attributes.insert(std::make_pair(caption, storage));
1.257 + return *this;
1.258 + }
1.259 +
1.260 /// \brief Edge reading rule
1.261 ///
1.262 /// Add an edge reading rule to reader.
1.263 @@ -2549,8 +2612,11 @@
1.264 LEMON_ASSERT(!_use_nodes, "Multiple usage of useNodes() member");
1.265 _use_nodes = true;
1.266 _writer_bits::DefaultConverter<typename Map::Value> converter;
1.267 - for (NodeIt n(_graph); n != INVALID; ++n) {
1.268 - _node_index.insert(std::make_pair(converter(map[n]), n));
1.269 + for (RedNodeIt n(_graph); n != INVALID; ++n) {
1.270 + _red_node_index.insert(std::make_pair(converter(map[n]), n));
1.271 + }
1.272 + for (BlueNodeIt n(_graph); n != INVALID; ++n) {
1.273 + _blue_node_index.insert(std::make_pair(converter(map[n]), n));
1.274 }
1.275 return *this;
1.276 }
1.277 @@ -2566,8 +2632,11 @@
1.278 checkConcept<concepts::ReadMap<Node, typename Map::Value>, Map>();
1.279 LEMON_ASSERT(!_use_nodes, "Multiple usage of useNodes() member");
1.280 _use_nodes = true;
1.281 - for (NodeIt n(_graph); n != INVALID; ++n) {
1.282 - _node_index.insert(std::make_pair(converter(map[n]), n));
1.283 + for (RedNodeIt n(_graph); n != INVALID; ++n) {
1.284 + _red_node_index.insert(std::make_pair(converter(map[n]), n));
1.285 + }
1.286 + for (BlueNodeIt n(_graph); n != INVALID; ++n) {
1.287 + _blue_node_index.insert(std::make_pair(converter(map[n]), n));
1.288 }
1.289 return *this;
1.290 }
1.291 @@ -2664,13 +2733,13 @@
1.292
1.293 void readRedNodes() {
1.294
1.295 - std::vector<int> map_index(_red_maps.size());
1.296 + std::vector<int> map_index(_red_node_maps.size());
1.297 int map_num, label_index;
1.298
1.299 char c;
1.300 if (!readLine() || !(line >> c) || c == '@') {
1.301 if (readSuccess() && line) line.putback(c);
1.302 - if (!_red_maps.empty())
1.303 + if (!_red_node_maps.empty())
1.304 throw FormatError("Cannot find map names");
1.305 return;
1.306 }
1.307 @@ -2691,12 +2760,12 @@
1.308 ++index;
1.309 }
1.310
1.311 - for (int i = 0; i < static_cast<int>(_red_maps.size()); ++i) {
1.312 + for (int i = 0; i < static_cast<int>(_red_node_maps.size()); ++i) {
1.313 std::map<std::string, int>::iterator jt =
1.314 - maps.find(_red_maps[i].first);
1.315 + maps.find(_red_node_maps[i].first);
1.316 if (jt == maps.end()) {
1.317 std::ostringstream msg;
1.318 - msg << "Map not found: " << _red_maps[i].first;
1.319 + msg << "Map not found: " << _red_node_maps[i].first;
1.320 throw FormatError(msg.str());
1.321 }
1.322 map_index[i] = jt->second;
1.323 @@ -2727,17 +2796,17 @@
1.324 if (line >> std::ws >> c)
1.325 throw FormatError("Extra character at the end of line");
1.326
1.327 - Node n;
1.328 + RedNode n;
1.329 if (!_use_nodes) {
1.330 n = _graph.addRedNode();
1.331 if (label_index != -1)
1.332 - _node_index.insert(std::make_pair(tokens[label_index], n));
1.333 + _red_node_index.insert(std::make_pair(tokens[label_index], n));
1.334 } else {
1.335 if (label_index == -1)
1.336 throw FormatError("Label map not found");
1.337 - typename std::map<std::string, Node>::iterator it =
1.338 - _node_index.find(tokens[label_index]);
1.339 - if (it == _node_index.end()) {
1.340 + typename std::map<std::string, RedNode>::iterator it =
1.341 + _red_node_index.find(tokens[label_index]);
1.342 + if (it == _red_node_index.end()) {
1.343 std::ostringstream msg;
1.344 msg << "Node with label not found: " << tokens[label_index];
1.345 throw FormatError(msg.str());
1.346 @@ -2745,8 +2814,8 @@
1.347 n = it->second;
1.348 }
1.349
1.350 - for (int i = 0; i < static_cast<int>(_red_maps.size()); ++i) {
1.351 - _red_maps[i].second->set(n, tokens[map_index[i]]);
1.352 + for (int i = 0; i < static_cast<int>(_red_node_maps.size()); ++i) {
1.353 + _red_node_maps[i].second->set(n, tokens[map_index[i]]);
1.354 }
1.355
1.356 }
1.357 @@ -2757,13 +2826,13 @@
1.358
1.359 void readBlueNodes() {
1.360
1.361 - std::vector<int> map_index(_blue_maps.size());
1.362 + std::vector<int> map_index(_blue_node_maps.size());
1.363 int map_num, label_index;
1.364
1.365 char c;
1.366 if (!readLine() || !(line >> c) || c == '@') {
1.367 if (readSuccess() && line) line.putback(c);
1.368 - if (!_blue_maps.empty())
1.369 + if (!_blue_node_maps.empty())
1.370 throw FormatError("Cannot find map names");
1.371 return;
1.372 }
1.373 @@ -2784,12 +2853,12 @@
1.374 ++index;
1.375 }
1.376
1.377 - for (int i = 0; i < static_cast<int>(_blue_maps.size()); ++i) {
1.378 + for (int i = 0; i < static_cast<int>(_blue_node_maps.size()); ++i) {
1.379 std::map<std::string, int>::iterator jt =
1.380 - maps.find(_blue_maps[i].first);
1.381 + maps.find(_blue_node_maps[i].first);
1.382 if (jt == maps.end()) {
1.383 std::ostringstream msg;
1.384 - msg << "Map not found: " << _blue_maps[i].first;
1.385 + msg << "Map not found: " << _blue_node_maps[i].first;
1.386 throw FormatError(msg.str());
1.387 }
1.388 map_index[i] = jt->second;
1.389 @@ -2820,17 +2889,17 @@
1.390 if (line >> std::ws >> c)
1.391 throw FormatError("Extra character at the end of line");
1.392
1.393 - Node n;
1.394 + BlueNode n;
1.395 if (!_use_nodes) {
1.396 n = _graph.addBlueNode();
1.397 if (label_index != -1)
1.398 - _node_index.insert(std::make_pair(tokens[label_index], n));
1.399 + _blue_node_index.insert(std::make_pair(tokens[label_index], n));
1.400 } else {
1.401 if (label_index == -1)
1.402 throw FormatError("Label map not found");
1.403 - typename std::map<std::string, Node>::iterator it =
1.404 - _node_index.find(tokens[label_index]);
1.405 - if (it == _node_index.end()) {
1.406 + typename std::map<std::string, BlueNode>::iterator it =
1.407 + _blue_node_index.find(tokens[label_index]);
1.408 + if (it == _blue_node_index.end()) {
1.409 std::ostringstream msg;
1.410 msg << "Node with label not found: " << tokens[label_index];
1.411 throw FormatError(msg.str());
1.412 @@ -2838,8 +2907,8 @@
1.413 n = it->second;
1.414 }
1.415
1.416 - for (int i = 0; i < static_cast<int>(_blue_maps.size()); ++i) {
1.417 - _blue_maps[i].second->set(n, tokens[map_index[i]]);
1.418 + for (int i = 0; i < static_cast<int>(_blue_node_maps.size()); ++i) {
1.419 + _blue_node_maps[i].second->set(n, tokens[map_index[i]]);
1.420 }
1.421
1.422 }
1.423 @@ -2924,39 +2993,26 @@
1.424
1.425 Edge e;
1.426 if (!_use_edges) {
1.427 -
1.428 - typename NodeIndex::iterator it;
1.429 -
1.430 - it = _node_index.find(source_token);
1.431 - if (it == _node_index.end()) {
1.432 + typename RedNodeIndex::iterator rit =
1.433 + _red_node_index.find(source_token);
1.434 + if (rit == _red_node_index.end()) {
1.435 std::ostringstream msg;
1.436 msg << "Item not found: " << source_token;
1.437 throw FormatError(msg.str());
1.438 }
1.439 - Node source = it->second;
1.440 - if (!_graph.red(source)) {
1.441 - std::ostringstream msg;
1.442 - msg << "Item is not red node: " << source_token;
1.443 - throw FormatError(msg.str());
1.444 - }
1.445 -
1.446 - it = _node_index.find(target_token);
1.447 - if (it == _node_index.end()) {
1.448 + RedNode source = rit->second;
1.449 + typename BlueNodeIndex::iterator it =
1.450 + _blue_node_index.find(target_token);
1.451 + if (it == _blue_node_index.end()) {
1.452 std::ostringstream msg;
1.453 msg << "Item not found: " << target_token;
1.454 throw FormatError(msg.str());
1.455 }
1.456 - Node target = it->second;
1.457 - if (!_graph.blue(target)) {
1.458 - std::ostringstream msg;
1.459 - msg << "Item is not red node: " << source_token;
1.460 - throw FormatError(msg.str());
1.461 - }
1.462 + BlueNode target = it->second;
1.463
1.464 // It is checked that source is red and
1.465 // target is blue, so this should be safe:
1.466 - e = _graph.addEdge(_graph.asRedNodeUnsafe(source),
1.467 - _graph.asBlueNodeUnsafe(target));
1.468 + e = _graph.addEdge(source, target);
1.469 if (label_index != -1)
1.470 _edge_index.insert(std::make_pair(tokens[label_index], e));
1.471 } else {