COIN-OR::LEMON - Graph Library

Changeset 1421:7a21e1414c38 in lemon-0.x for src/lemon/lemon_writer.h


Ignore:
Timestamp:
05/14/05 19:39:37 (19 years ago)
Author:
Balazs Dezso
Branch:
default
Phase:
public
Convert:
svn:c9d7d8f5-90d6-0310-b91f-818b3a526b0e/lemon/trunk@1891
Message:

IO with undirected edgesets and undirected graphs.
Missing features:

InfoReader?,
aliased edges in undir edgesets

File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/lemon/lemon_writer.h

    r1411 r1421  
    3232#include <lemon/error.h>
    3333#include <lemon/invalid.h>
     34#include <lemon/graph_utils.h>
    3435#include <lemon/bits/item_writer.h>
     36#include <lemon/utility.h>
     37#include <lemon/maps.h>
    3538
    3639
     
    164167      : Parent(_writer) {}
    165168
    166     // Writers
    167 
    168169    template <typename _Item>   
    169170    class WriterBase {
     
    185186      typedef _Item Item;
    186187     
    187       const Map& map;
     188      typename SmartConstReference<Map>::Type map;
    188189      Writer writer;
    189190
     
    307308    /// Add a new node map writer command for the writer.
    308309    template <typename Map>
    309     NodeSetWriter& writeMap(std::string name, const Map& map) {
    310       return writeMap<typename Traits::
     310    NodeSetWriter& writeNodeMap(std::string name, const Map& map) {
     311      return writeNodeMap<typename Traits::
    311312        template Writer<typename Map::Value>, Map>(name, map);
    312313    }
     
    316317    /// Add a new node map writer command for the writer.
    317318    template <typename Writer, typename Map>
    318     NodeSetWriter& writeMap(std::string name, const Map& map,
    319                              const Writer& writer = Writer()) {
     319    NodeSetWriter& writeNodeMap(std::string name, const Map& map,
     320                            const Writer& writer = Writer()) {
    320321      writers.push_back(
    321322        make_pair(name, new MapWriter<Item, Map, Writer>(map, writer)));
     
    395396    bool forceIdMap;
    396397   
    397     const Graph& graph;   
     398    typename SmartConstReference<Graph>::Type graph;   
    398399    std::string id;
    399400
     
    401402
    402403  /// \ingroup io_group
    403   /// \brief SectionWriter for writing a graph's edgeset.
    404   ///
    405   /// The lemon format can store multiple graph edgesets with several maps.
     404  /// \brief SectionWriter for writing a graph's edgesets.
     405  ///
     406  /// The lemon format can store multiple graph edgesets with several maps. 
    406407  /// The edgeset section's header line is \c \@edgeset \c edgeset_id, but the
    407408  /// \c edgeset_id may be empty.
     
    414415  /// If the edgeset contains an \c "id" named map then it will be regarded
    415416  /// as id map. This map should contain only unique values and when the
    416   /// \c writeId() member will be called with a edge it will write it's id.
     417  /// \c writeId() member will be called with an edge it will write it's id.
    417418  /// Otherwise if the \c _forceIdMap constructor parameter is true then
    418419  /// the id map will be the id in the graph.
     
    437438    /// attach it into the given LemonWriter. It will write node ids by
    438439    /// the \c _nodeIdWriter. If the \c _forceIdMap parameter is true
    439     /// then the writer will write own id map when the user does not give
     440    /// then the writer will write own id map if the user does not give
    440441    /// "id" named map.
    441442    template <typename NodeIdWriter>
     
    465466  public:
    466467
    467     /// \brief Add a new node map writer command for the writer.
    468     ///
    469     /// Add a new node map writer command for the writer.
     468    /// \brief Add a new edge map writer command for the writer.
     469    ///
     470    /// Add a new edge map writer command for the writer.
    470471    template <typename Map>
    471     EdgeSetWriter& writeMap(std::string name, const Map& map) {
    472       return writeMap<typename Traits::
     472    EdgeSetWriter& writeEdgeMap(std::string name, const Map& map) {
     473      return writeEdgeMap<typename Traits::
    473474        template Writer<typename Map::Value>, Map>(name, map);
    474475    }
    475476
    476     /// \brief Add a new node map writer command for the writer.
    477     ///
    478     /// Add a new node map writer command for the writer.
     477    /// \brief Add a new edge map writer command for the writer.
     478    ///
     479    /// Add a new edge map writer command for the writer.
    479480    template <typename Writer, typename Map>
    480     EdgeSetWriter& writeMap(std::string name, const Map& map,
    481                              const Writer& writer = Writer()) {
     481    EdgeSetWriter& writeEdgeMap(std::string name, const Map& map,
     482                            const Writer& writer = Writer()) {
    482483      writers.push_back(
    483484        make_pair(name, new MapWriter<Item, Map, Writer>(map, writer)));
     
    562563    bool forceIdMap;
    563564   
    564     const Graph& graph;   
     565    typename SmartConstReference<Graph>::Type graph;   
     566    std::string id;
     567
     568    std::auto_ptr<IdWriterBase<typename Graph::Node> > nodeIdWriter;
     569  };
     570
     571  /// \ingroup io_group
     572  /// \brief SectionWriter for writing a undirected edgeset.
     573  ///
     574  /// The lemon format can store multiple undirected edgesets with several
     575  /// maps. The undirected edgeset section's header line is \c \@undiredgeset
     576  /// \c undiredgeset_id, but the \c undiredgeset_id may be empty.
     577  ///
     578  /// The first line of the section contains the names of the maps separated
     579  /// with white spaces. Each next lines describes an undirected edge in the
     580  /// edgeset. The line contains the two connected nodes' id and the mapped
     581  /// values for each undirected map.
     582  ///
     583  /// The section can handle the directed as a syntactical sugar. Two
     584  /// undirected edge map describes one directed edge map. This two maps
     585  /// are the forward map and the backward map and the names of this map
     586  /// is near the same just with a prefix \c '+' or \c '-' character
     587  /// difference.
     588  ///
     589  /// If the edgeset contains an \c "id" named map then it will be regarded
     590  /// as id map. This map should contain only unique values and when the
     591  /// \c writeId() member will be called with an undirected edge it will
     592  /// write it's id. Otherwise if the \c _forceIdMap constructor parameter
     593  /// is true then the id map will be the id in the graph.
     594  ///
     595  /// The undirected edgeset writer needs a node id writer to identify
     596  /// which nodes have to be connected. If a NodeSetWriter can write the
     597  /// nodes' id, it will be able to use with this class.
     598  ///
     599  /// \relates LemonWriter
     600  template <typename _Graph, typename _Traits = DefaultWriterTraits>
     601  class UndirEdgeSetWriter : public CommonSectionWriterBase {
     602    typedef CommonSectionWriterBase Parent;
     603  public:
     604
     605    typedef _Graph Graph;
     606    typedef _Traits Traits;
     607    typedef typename Graph::UndirEdge Item;
     608
     609    /// \brief Constructor.
     610    ///
     611    /// Constructor for UndirEdgeSetWriter. It creates the UndirEdgeSetWriter
     612    /// and attach it into the given LemonWriter. It will write node ids by
     613    /// the \c _nodeIdWriter. If the \c _forceIdMap parameter is true
     614    /// then the writer will write own id map if the user does not give
     615    /// "id" named map.
     616    template <typename NodeIdWriter>
     617    UndirEdgeSetWriter(LemonWriter& _writer, const Graph& _graph,
     618                       const NodeIdWriter& _nodeIdWriter,
     619                       const std::string& _id = std::string(),
     620                       bool _forceIdMap = true)
     621      : Parent(_writer), idMap(0), forceIdMap(_forceIdMap),
     622        graph(_graph), id(_id),
     623        nodeIdWriter(new IdWriter<typename Graph::Node, NodeIdWriter>
     624                     (_nodeIdWriter)) {}
     625
     626    /// \brief Destructor.
     627    ///
     628    /// Destructor for UndirEdgeSetWriter.
     629    virtual ~UndirEdgeSetWriter() {
     630      typename MapWriters::iterator it;
     631      for (it = writers.begin(); it != writers.end(); ++it) {
     632        delete it->second;
     633      }
     634    }
     635
     636  private:
     637    UndirEdgeSetWriter(const UndirEdgeSetWriter&);
     638    void operator=(const UndirEdgeSetWriter&);
     639
     640  public:
     641
     642    /// \brief Add a new undirected edge map writer command for the writer.
     643    ///
     644    /// Add a new undirected map writer command for the writer.
     645    template <typename Map>
     646    UndirEdgeSetWriter& writeUndirEdgeMap(std::string name, const Map& map) {
     647      return writeUndirEdgeMap<typename Traits::
     648        template Writer<typename Map::Value>, Map>(name, map);
     649    }
     650
     651    /// \brief Add a new undirected map writer command for the writer.
     652    ///
     653    /// Add a new undirected map writer command for the writer.
     654    template <typename Writer, typename Map>
     655    UndirEdgeSetWriter& writeUndirEdgeMap(std::string name, const Map& map,
     656                                          const Writer& writer = Writer()) {
     657      writers.push_back(
     658        make_pair(name, new MapWriter<Item, Map, Writer>(map, writer)));
     659      return *this;
     660    }
     661
     662    /// \brief Add a new directed edge map writer command for the writer.
     663    ///
     664    /// Add a new directed map writer command for the writer.
     665    template <typename Map>
     666    UndirEdgeSetWriter& writeEdgeMap(std::string name, const Map& map) {
     667      writeUndirEdgeMap("+" + name, composeMap(forwardMap(graph), map));
     668      writeUndirEdgeMap("-" + name, composeMap(backwardMap(graph), map));
     669      return *this;
     670    }
     671
     672    /// \brief Add a new directed map writer command for the writer.
     673    ///
     674    /// Add a new directed map writer command for the writer.
     675    template <typename Writer, typename Map>
     676    UndirEdgeSetWriter& writeEdgeMap(std::string name, const Map& map,
     677                                     const Writer& writer = Writer()) {
     678      writeUndirEdge("+" + name, composeMap(forwardMap(graph), map), writer);
     679      writeUndirEdge("-" + name, composeMap(forwardMap(graph), map), writer);
     680      return *this;
     681    }
     682
     683  protected:
     684
     685    /// \brief The header of the section.
     686    ///
     687    /// It gives back the header of the section.
     688    virtual std::string header() {
     689      return "@undiredgeset " + id;
     690    }
     691
     692    /// \brief  Writer function of the section.
     693    ///
     694    /// Write the content of the section.
     695    virtual void write(std::ostream& os) {
     696      for (int i = 0; i < (int)writers.size(); ++i) {
     697        if (writers[i].first == "id") {
     698          idMap = writers[i].second;
     699          forceIdMap = false;
     700          break;
     701        }
     702      }
     703      os << "\t\t";
     704      if (forceIdMap) {
     705        os << "id\t";
     706      }
     707      for (int i = 0; i < (int)writers.size(); ++i) {
     708        os << writers[i].first << '\t';
     709      }
     710      os << std::endl;
     711      for (typename Graph::UndirEdgeIt it(graph); it != INVALID; ++it) {
     712        nodeIdWriter->write(os, graph.source(it));
     713        os << '\t';
     714        nodeIdWriter->write(os, graph.target(it));
     715        os << '\t';
     716        if (forceIdMap) {
     717          os << graph.id(it) << '\t';
     718        }
     719        for (int i = 0; i < (int)writers.size(); ++i) {
     720          writers[i].second->write(os, it);
     721          os << '\t';
     722        }
     723        os << std::endl;
     724      }
     725    }
     726
     727  public:
     728
     729    /// \brief Returns true if the undirected edgeset can write the ids of
     730    /// the edges.
     731    ///
     732    /// Returns true if the undirected edgeset can write the ids of the
     733    /// undirected edges. It is possible only if an "id" named map was
     734    /// written or the \c _forceIdMap constructor parameter was true.
     735    bool isIdWriter() const {
     736      return forceIdMap || idMap != 0;
     737    }
     738
     739    /// \brief Write the id of the given undirected edge.
     740    ///
     741    /// It writes the id of the given undirected edge. If there was written
     742    /// an "id" named map then it will write the map value belongs to the
     743    /// undirected edge. Otherwise if the \c forceId parameter was true it
     744    /// will write its id in the graph.
     745    void writeId(std::ostream& os, const Item& item) const {
     746      if (forceIdMap) {
     747        os << graph.id(item);
     748      } else {
     749        idMap->write(os, item);
     750      }
     751    }
     752
     753  private:
     754
     755    typedef std::vector<std::pair<std::string, WriterBase<Item>*> > MapWriters;
     756    MapWriters writers;
     757
     758    WriterBase<Item>* idMap;
     759    bool forceIdMap;
     760   
     761    typename SmartConstReference<Graph>::Type graph;   
    565762    std::string id;
    566763
     
    618815    /// \brief Header checking function.
    619816    ///
    620     /// It gives back true when the header line start with \c @nodes,
     817    /// It gives back true when the header line start with \c \@nodes,
    621818    /// and the header line's id and the writer's id are the same.
    622819    virtual std::string header() {
     
    645842
    646843  /// \ingroup io_group
    647   /// \brief SectionWriter for writeing labeled edges.
     844  /// \brief SectionWriter for writing labeled edges.
    648845  ///
    649846  /// The edges section's header line is \c \@edges \c edges_id, but the
     
    682879  public:
    683880
    684     /// \brief Add an edge writer command for the NodeWriter.
    685     ///
    686     /// Add an edge writer command for the NodeWriter.
     881    /// \brief Add an edge writer command for the EdgeWriter.
     882    ///
     883    /// Add an edge writer command for the EdgeWriter.
    687884    void writeEdge(const std::string& name, const Item& item) {
    688885      writers.push_back(make_pair(name, &item));
     
    693890    /// \brief Header checking function.
    694891    ///
    695     /// It gives back true when the header line start with \c @nodes,
     892    /// It gives back true when the header line start with \c \@edges,
     893    /// and the header line's id and the writer's id are the same.
     894    virtual std::string header() {
     895      return "@edges " + id;
     896    }
     897
     898    /// \brief  Writer function of the section.
     899    ///
     900    /// Write the content of the section.
     901    virtual void write(std::ostream& os) {
     902      for (int i = 0; i < (int)writers.size(); ++i) {
     903        os << writers[i].first << ' ';
     904        idWriter->write(os, *(writers[i].second));
     905        os << std::endl;
     906      }
     907    }
     908   
     909  private:
     910
     911    std::string id;
     912
     913    typedef std::vector<std::pair<std::string, const Item*> > ItemWriters;
     914    ItemWriters writers;
     915
     916    std::auto_ptr<IdWriterBase<Item> > idWriter;
     917  };
     918
     919  /// \ingroup io_group
     920  /// \brief SectionWriter for writing labeled undirected edges.
     921  ///
     922  /// The undirected edges section's header line is \c \@undiredges
     923  /// \c undiredges_id, but the \c undiredges_id may be empty.
     924  ///
     925  /// Each line in the section contains the label of the undirected edge and
     926  /// then the undirected edge id.
     927  ///
     928  /// \relates LemonWriter
     929  template <typename _Graph>
     930  class UndirEdgeWriter : public CommonSectionWriterBase {
     931    typedef CommonSectionWriterBase Parent;
     932    typedef _Graph Graph;
     933    typedef typename Graph::UndirEdge Item;
     934  public:
     935   
     936    /// \brief Constructor.
     937    ///
     938    /// Constructor for UndirEdgeWriter. It creates the UndirEdgeWriter and
     939    /// attach it into the given LemonWriter. The given \c _IdWriter
     940    /// will write the undirected edges' id what can be an undirected
     941    /// edgeset writer.
     942    template <typename _IdWriter>
     943    UndirEdgeWriter(LemonWriter& _writer, const _IdWriter& _idWriter,
     944               const std::string& _id = std::string())
     945      : Parent(_writer), id(_id),
     946        idWriter(new IdWriter<typename Graph::UndirEdge, _IdWriter>
     947                 (_idWriter)) {}
     948
     949    /// \brief Destructor.
     950    ///
     951    /// Destructor for UndirEdgeWriter.
     952    virtual ~UndirEdgeWriter() {}
     953  private:
     954    UndirEdgeWriter(const UndirEdgeWriter&);
     955    void operator=(const UndirEdgeWriter&);
     956
     957  public:
     958
     959    /// \brief Add an undirected edge writer command for the UndirEdgeWriter.
     960    ///
     961    /// Add an edge writer command for the UndirEdgeWriter.
     962    void writeUndirEdge(const std::string& name, const Item& item) {
     963      writers.push_back(make_pair(name, &item));
     964    }
     965
     966  protected:
     967
     968    /// \brief Header checking function.
     969    ///
     970    /// It gives back true when the header line start with \c \@undiredges,
    696971    /// and the header line's id and the writer's id are the same.
    697972    virtual std::string header() {
Note: See TracChangeset for help on using the changeset viewer.