lemon/matrix_maps.h
author deba
Mon, 15 May 2006 09:49:51 +0000
changeset 2084 59769591eb60
parent 2072 224d3781b00b
child 2088 68f8d17ced51
permissions -rw-r--r--
Documentation improvements

Rearrangements:
IO modules
Algorithms

New documentation:
SwapBpUGraphAdaptor

Demos:
strongly_connected_orientation.cc

Benchmarks:
swap_bipartite_bench.cc
     1 /* -*- C++ -*-
     2  *
     3  * This file is a part of LEMON, a generic C++ optimization library
     4  *
     5  * Copyright (C) 2003-2006
     6  * Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport
     7  * (Egervary Research Group on Combinatorial Optimization, EGRES).
     8  *
     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.
    12  *
    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
    15  * purpose.
    16  *
    17  */
    18 
    19 #ifndef LEMON_MATRIX_MAPS_H
    20 #define LEMON_MATRIX_MAPS_H
    21 
    22 
    23 #include <vector>
    24 #include <lemon/bits/utility.h>
    25 #include <lemon/maps.h>
    26 
    27 #include <lemon/concept/matrix_maps.h>
    28 
    29 /// \file
    30 /// \ingroup matrices
    31 /// \brief Maps indexed with pairs of items.
    32 ///
    33 /// \todo This file has the same name as the concept file in concept/,
    34 ///  and this is not easily detectable in docs...
    35 namespace lemon {
    36 
    37   /// \brief Map for the coloumn view of the matrix
    38   ///
    39   /// \ingroup matrices
    40   /// Map for the coloumn view of the matrix.
    41   ///
    42   template <typename _MatrixMap>
    43   class MatrixRowMap : public MatrixMapTraits<_MatrixMap> {
    44   public:
    45     typedef _MatrixMap MatrixMap;
    46     typedef typename MatrixMap::SecondKey Key;
    47     typedef typename MatrixMap::Value Value;
    48 
    49 
    50     /// \brief Constructor of the row map
    51     ///
    52     /// Constructor of the row map.
    53     MatrixRowMap(MatrixMap& _matrix, typename MatrixMap::FirstKey _row) 
    54       : matrix(_matrix), row(_row) {}
    55 
    56     /// \brief Subscription operator
    57     ///
    58     /// Subscription operator.
    59     typename MatrixMapTraits<MatrixMap>::ReturnValue
    60     operator[](Key col) {
    61       return matrix(row, col);
    62     }
    63 
    64     /// \brief Setter function
    65     ///
    66     /// Setter function.
    67     void set(Key col, const Value& val) {
    68       matrix.set(row, col, val);
    69     }
    70       
    71     /// \brief Subscription operator
    72     ///
    73     /// Subscription operator.
    74     typename MatrixMapTraits<MatrixMap>::ConstReturnValue
    75     operator[](Key col) const {
    76       return matrix(row, col);
    77     }
    78 
    79   private:
    80     MatrixMap& matrix;
    81     typename MatrixMap::FirstKey row;
    82   };
    83 
    84   /// \brief Map for the row view of the matrix
    85   ///
    86   /// \ingroup matrices
    87   /// Map for the row view of the matrix.
    88   ///
    89   template <typename _MatrixMap>
    90   class ConstMatrixRowMap : public MatrixMapTraits<_MatrixMap> {
    91   public:
    92     typedef _MatrixMap MatrixMap;
    93     typedef typename MatrixMap::SecondKey Key;
    94     typedef typename MatrixMap::Value Value;
    95 
    96 
    97     /// \brief Constructor of the row map
    98     ///
    99     /// Constructor of the row map.
   100     ConstMatrixRowMap(const MatrixMap& _matrix, 
   101 		      typename MatrixMap::FirstKey _row) 
   102       : matrix(_matrix), row(_row) {}
   103 
   104     /// \brief Subscription operator
   105     ///
   106     /// Subscription operator.
   107     typename MatrixMapTraits<MatrixMap>::ConstReturnValue
   108     operator[](Key col) const {
   109       return matrix(row, col);
   110     }
   111 
   112   private:
   113     const MatrixMap& matrix;
   114     typename MatrixMap::FirstKey row;
   115   };
   116 
   117   /// \ingroup matrices
   118   ///
   119   /// \brief Gives back a row view of the matrix map
   120   ///
   121   /// Gives back a row view of the matrix map.
   122   ///
   123   /// \sa MatrixRowMap
   124   /// \sa ConstMatrixRowMap
   125   template <typename MatrixMap>
   126   MatrixRowMap<MatrixMap> matrixRowMap(MatrixMap& matrixMap,
   127 				       typename MatrixMap::FirstKey row) {
   128     return MatrixRowMap<MatrixMap>(matrixMap, row);
   129   }
   130 
   131   template <typename MatrixMap>
   132   ConstMatrixRowMap<MatrixMap>
   133   matrixRowMap(const MatrixMap& matrixMap, typename MatrixMap::FirstKey row) {
   134     return ConstMatrixRowMap<MatrixMap>(matrixMap, row);
   135   }
   136 
   137   /// \brief Map for the column view of the matrix
   138   ///
   139   /// \ingroup matrices
   140   /// Map for the column view of the matrix.
   141   ///
   142   template <typename _MatrixMap>
   143   class MatrixColMap : public MatrixMapTraits<_MatrixMap> {
   144   public:
   145     typedef _MatrixMap MatrixMap;
   146     typedef typename MatrixMap::FirstKey Key;
   147     typedef typename MatrixMap::Value Value;
   148 
   149     /// \brief Constructor of the column map
   150     ///
   151     /// Constructor of the column map.
   152     MatrixColMap(MatrixMap& _matrix, typename MatrixMap::SecondKey _col) 
   153       : matrix(_matrix), col(_col) {}
   154 
   155     /// \brief Subscription operator
   156     ///
   157     /// Subscription operator.
   158     typename MatrixMapTraits<MatrixMap>::ReturnValue
   159     operator[](Key row) {
   160       return matrix(row, col);
   161     }
   162 
   163     /// \brief Setter function
   164     ///
   165     /// Setter function.
   166     void set(Key row, const Value& val) {
   167       matrix.set(row, col, val);
   168     }
   169       
   170     /// \brief Subscription operator
   171     ///
   172     /// Subscription operator.
   173     typename MatrixMapTraits<MatrixMap>::ConstReturnValue
   174     operator[](Key row) const {
   175       return matrix(row, col);
   176     }
   177 
   178   private:
   179     MatrixMap& matrix;
   180     typename MatrixMap::SecondKey col;
   181   };
   182 
   183   /// \brief Map for the column view of the matrix
   184   ///
   185   /// \ingroup matrices
   186   /// Map for the column view of the matrix.
   187   ///
   188   template <typename _MatrixMap>
   189   class ConstMatrixColMap : public MatrixMapTraits<_MatrixMap> {
   190   public:
   191     typedef _MatrixMap MatrixMap;
   192     typedef typename MatrixMap::FirstKey Key;
   193     typedef typename MatrixMap::Value Value;
   194 
   195     /// \brief Constructor of the column map
   196     ///
   197     /// Constructor of the column map.
   198     ConstMatrixColMap(const MatrixMap& _matrix, 
   199 		      typename MatrixMap::SecondKey _col) 
   200       : matrix(_matrix), col(_col) {}
   201 
   202     /// \brief Subscription operator
   203     ///
   204     /// Subscription operator.
   205     typename MatrixMapTraits<MatrixMap>::ConstReturnValue
   206     operator[](Key row) const {
   207       return matrix(row, col);
   208     }
   209 
   210   private:
   211     const MatrixMap& matrix;
   212     typename MatrixMap::SecondKey col;
   213   };
   214 
   215   /// \ingroup matrices
   216   ///
   217   /// \brief Gives back a column view of the matrix map
   218   ///
   219   /// Gives back a column view of the matrix map.
   220   ///
   221   /// \sa MatrixColMap
   222   /// \sa ConstMatrixColMap
   223   template <typename MatrixMap>
   224   MatrixColMap<MatrixMap> matrixColMap(MatrixMap& matrixMap,
   225 				       typename MatrixMap::SecondKey col) {
   226     return MatrixColMap<MatrixMap>(matrixMap, col);
   227   }
   228 
   229   template <typename MatrixMap>
   230   ConstMatrixColMap<MatrixMap> 
   231   matrixColMap(const MatrixMap& matrixMap, typename MatrixMap::SecondKey col) {
   232     return ConstMatrixColMap<MatrixMap>(matrixMap, col);
   233   }
   234 
   235   /// \brief Container for store values for each ordered pair of graph items
   236   ///
   237   /// \ingroup matrices
   238   /// This data structure can strore for each pair of the same item
   239   /// type a value. It increase the size of the container when the 
   240   /// associated graph modified, so it updated automaticly whenever
   241   /// it is needed.
   242   template <typename _Graph, typename _Item, typename _Value>
   243   class DynamicMatrixMap 
   244     : protected ItemSetTraits<_Graph, _Item>::ItemNotifier::ObserverBase {
   245   public:
   246     typedef typename ItemSetTraits<_Graph, _Item>::ItemNotifier::ObserverBase 
   247     Parent;
   248 
   249     typedef _Graph Graph;
   250     typedef _Item Key;
   251 
   252     typedef _Item FirstKey;
   253     typedef _Item SecondKey;
   254     typedef _Value Value;
   255 
   256     typedef True ReferenceMapTag;
   257 
   258   private:
   259 		
   260     typedef std::vector<Value> Container;
   261 
   262   public:
   263 
   264     typedef typename Container::reference Reference;
   265     typedef typename Container::const_reference ConstReference;
   266 
   267     /// \brief Creates an item matrix for the given graph
   268     ///
   269     /// Creates an item matrix for the given graph.
   270     DynamicMatrixMap(const Graph& _graph) 
   271       : values(size(_graph.maxId(Key()) + 1)) {
   272       Parent::attach(_graph.getNotifier(Key()));
   273     }
   274 
   275     /// \brief Creates an item matrix for the given graph
   276     ///
   277     /// Creates an item matrix for the given graph and assigns for each
   278     /// pairs of keys the given parameter.
   279     DynamicMatrixMap(const Graph& _graph, const Value& _val) 
   280       : values(size(_graph.maxId(Key()) + 1), _val) {
   281       Parent::attach(_graph.getNotifier(Key()));
   282     }
   283 
   284     ///\brief The assignement operator.
   285     ///
   286     ///It allow to assign a map to an other.
   287     DynamicMatrixMap& operator=(const DynamicMatrixMap& _cmap){
   288       return operator=<DynamicMatrixMap>(_cmap);
   289     }
   290       
   291     ///\brief Template assignement operator.
   292     ///
   293     ///It copy the element of the given map to its own container.  The
   294     ///type of the two map shall be the same.
   295     template <typename CMap>
   296     DynamicMatrixMap& operator=(const CMap& _cmap){
   297       checkConcept<concept::ReadMatrixMap<FirstKey, SecondKey, Value>, CMap>();
   298       typename Parent::Notifier* notifier = Parent::getNotifier();
   299       Key first, second;
   300       for(notifier->first(first); first != INVALID; 
   301           notifier->next(first)){
   302         for(notifier->first(second); second != INVALID; 
   303             notifier->next(second)){
   304           set(first, second, _cmap(first, second));
   305         }
   306       }
   307       return *this;
   308     }
   309 
   310     /// \brief Gives back the value assigned to the \c first - \c second
   311     /// ordered pair.
   312     ///
   313     /// Gives back the value assigned to the \c first - \c second ordered pair.
   314     ConstReference operator()(const Key& first, const Key& second) const {
   315       return values[index(Parent::getNotifier()->id(first), 
   316                           Parent::getNotifier()->id(second))];
   317     }
   318     
   319     /// \brief Gives back the value assigned to the \c first - \c second
   320     /// ordered pair.
   321     ///
   322     /// Gives back the value assigned to the \c first - \c second ordered pair.
   323     Reference operator()(const Key& first, const Key& second) {
   324       return values[index(Parent::getNotifier()->id(first), 
   325                           Parent::getNotifier()->id(second))];
   326     }
   327 
   328     /// \brief Setter function for the matrix map.
   329     ///
   330     /// Setter function for the matrix map.
   331     void set(const Key& first, const Key& second, const Value& val) {
   332       values[index(Parent::getNotifier()->id(first), 
   333                    Parent::getNotifier()->id(second))] = val;
   334     }
   335 
   336   protected:
   337 
   338     static int index(int i, int j) {
   339       if (i < j) {
   340 	return j * j + i;
   341       } else {
   342 	return i * i + i + j;
   343       }
   344     }
   345 
   346     static int size(int s) {
   347       return s * s;
   348     }
   349 
   350     virtual void add(const Key& key) {
   351       if (size(Parent::getNotifier()->id(key) + 1) >= (int)values.size()) {
   352 	values.resize(size(Parent::getNotifier()->id(key) + 1));	
   353       }
   354     }
   355 
   356     virtual void erase(const Key&) {}
   357 
   358     virtual void build() {
   359       values.resize(size(Parent::getNotifier()->maxId() + 1));
   360     }
   361 
   362     virtual void clear() {
   363       values.clear();
   364     }   
   365     
   366   private:
   367     std::vector<Value> values;
   368   };
   369 
   370   /// \brief Container for store values for each unordered pair of graph items
   371   ///
   372   /// \ingroup matrices
   373   /// This data structure can strore for each pair of the same item
   374   /// type a value. It increase the size of the container when the 
   375   /// associated graph modified, so it updated automaticly whenever
   376   /// it is needed. 
   377   template <typename _Graph, typename _Item, typename _Value>
   378   class DynamicSymMatrixMap 
   379     : protected ItemSetTraits<_Graph, _Item>::ItemNotifier::ObserverBase {
   380   public:
   381     typedef typename ItemSetTraits<_Graph, _Item>::ItemNotifier::ObserverBase 
   382     Parent;
   383 
   384     typedef _Graph Graph;
   385     typedef _Item Key;
   386 
   387     typedef _Item FirstKey;
   388     typedef _Item SecondKey;
   389     typedef _Value Value;
   390 
   391     typedef True ReferenceMapTag;
   392 
   393   private:
   394 		
   395     typedef std::vector<Value> Container;
   396 
   397   public:
   398 
   399     typedef typename Container::reference Reference;
   400     typedef typename Container::const_reference ConstReference;
   401 
   402     /// \brief Creates an item matrix for the given graph
   403     ///
   404     /// Creates an item matrix for the given graph.
   405     DynamicSymMatrixMap(const Graph& _graph) 
   406       : values(size(_graph.maxId(Key()) + 1)) {
   407       Parent::attach(_graph.getNotifier(Key()));
   408     }
   409 
   410     /// \brief Creates an item matrix for the given graph
   411     ///
   412     /// Creates an item matrix for the given graph and assigns for each
   413     /// pairs of keys the given parameter.
   414     DynamicSymMatrixMap(const Graph& _graph, const Value& _val) 
   415       : values(size(_graph.maxId(Key()) + 1), _val) {
   416       Parent::attach(_graph.getNotifier(Key()));
   417     }
   418 
   419 
   420     ///\brief The assignement operator.
   421     ///
   422     ///It allow to assign a map to an other.
   423     ///
   424     DynamicSymMatrixMap& operator=(const DynamicSymMatrixMap& _cmap){
   425       return operator=<DynamicSymMatrixMap>(_cmap);
   426     }
   427       
   428     ///\brief Template assignement operator.
   429     ///
   430     ///It copy the element of the given map to its own container.  The
   431     ///type of the two map shall be the same.
   432     template <typename CMap>
   433     DynamicSymMatrixMap& operator=(const CMap& _cmap){
   434       checkConcept<concept::ReadMatrixMap<FirstKey, SecondKey, Value>, CMap>();
   435       typename Parent::Notifier* notifier = Parent::getNotifier();
   436       Key first, second;
   437       for(notifier->first(first); first != INVALID; 
   438           notifier->next(first)){
   439         for(notifier->first(second); second != first; 
   440             notifier->next(second)){
   441           set(first, second, _cmap(first, second));
   442         }
   443         set(first, first, _cmap(first, first));        
   444       }
   445       return *this;
   446     }
   447 
   448     /// \brief Gives back the value assigned to the \c first - \c second
   449     /// unordered pair.
   450     ///
   451     /// Gives back the value assigned to the \c first - \c second unordered 
   452     /// pair.
   453     ConstReference operator()(const Key& first, const Key& second) const {
   454       return values[index(Parent::getNotifier()->id(first), 
   455                           Parent::getNotifier()->id(second))];
   456     }
   457     
   458     /// \brief Gives back the value assigned to the \c first - \c second
   459     /// unordered pair.
   460     ///
   461     /// Gives back the value assigned to the \c first - \c second unordered 
   462     /// pair.
   463     Reference operator()(const Key& first, const Key& second) {
   464       return values[index(Parent::getNotifier()->id(first), 
   465                           Parent::getNotifier()->id(second))];
   466     }
   467 
   468     /// \brief Setter function for the matrix map.
   469     ///
   470     /// Setter function for the matrix map.
   471     ///
   472     void set(const Key& first, const Key& second, const Value& val) {
   473       values[index(Parent::getNotifier()->id(first), 
   474                    Parent::getNotifier()->id(second))] = val;
   475     }
   476 
   477   protected:
   478 
   479     static int index(int i, int j) {
   480       if (i < j) {
   481 	return j * (j + 1) / 2 + i;
   482       } else {
   483 	return i * (i + 1) / 2 + j;
   484       }
   485     }
   486 
   487     static int size(int s) {
   488       return s * (s + 1) / 2;
   489     }
   490 
   491     virtual void add(const Key& key) {
   492       if (size(Parent::getNotifier()->id(key) + 1) >= (int)values.size()) {
   493 	values.resize(size(Parent::getNotifier()->id(key) + 1));	
   494       }
   495     }
   496 
   497     virtual void erase(const Key&) {}
   498 
   499     virtual void build() {
   500       values.resize(size(Parent::getNotifier()->maxId() + 1));
   501     }
   502 
   503     virtual void clear() {
   504       values.clear();
   505     }   
   506     
   507   private:
   508     std::vector<Value> values;
   509   };
   510   
   511   ///\brief Dynamic Asymmetric Matrix Map.
   512   ///
   513   ///\ingroup matrices
   514   ///Dynamic Asymmetric Matrix Map.  Container for store values for each
   515   ///ordered pair of containers items.  This data structure can store
   516   ///data with different key types from different container types. It
   517   ///increases the size of the container if the linked containers
   518   ///content change, so it is updated automaticly whenever it is
   519   ///needed.
   520   ///
   521   ///This map meet with the concept::ReferenceMatrixMap<typename K1,
   522   ///typename K2, typename V, typename R, typename CR> called as
   523   ///"ReferenceMatrixMap".
   524   ///
   525   ///\param _FirstContainer the desired type of first container. It is
   526   ///ususally a Graph type, but can be any type with alteration
   527   ///property.
   528   ///  
   529   ///\param _FirstContainerItem the nested type of the
   530   ///FirstContainer. It is usually a graph item as Node, Edge,
   531   ///etc. This type will be the FirstKey type.
   532   ///
   533   ///\param _SecondContainer the desired type of the second
   534   ///container. It is usualy a Graph type, but can be any type with
   535   ///alteration property.
   536   ///
   537   ///\param _SecondContainerItem the nested type of the
   538   ///SecondContainer. It is usually a graph item such as Node, Edge,
   539   ///UEdge, etc. This type will be the SecondKey type.
   540   ///
   541   ///\param _Value the type of the strored values in the container.
   542   ///
   543   /// \author Janos Nagy
   544   template <typename _FirstContainer, typename _FirstContainerItem, 
   545             typename _SecondContainer, typename _SecondContainerItem, 
   546             typename _Value>
   547   class DynamicAsymMatrixMap{
   548   public:
   549 
   550     ///The first key type.
   551     typedef _FirstContainerItem FirstKey;
   552       
   553     ///The second key type.
   554     typedef _SecondContainerItem SecondKey;
   555       
   556     ///The value type of the map.
   557     typedef _Value Value;
   558       
   559     ///Indicates it is a reference map.
   560     typedef True ReferenceMapTag;
   561     
   562   protected:
   563       
   564     ///\brief Proxy class for the first key type.
   565     ///
   566     ///The proxy class belongs to the FirstKey type. It is necessary because
   567     ///if one want use the same conatainer types and same nested types but on
   568     ///other instances of containers than due to the type equiality of nested
   569     ///types it requires a proxy mechanism. 
   570     class FirstKeyProxy 
   571       : protected 
   572     ItemSetTraits<_FirstContainer,_FirstContainerItem>::
   573     ItemNotifier::ObserverBase 
   574     {
   575         
   576     public:
   577 
   578       friend class DynamicAsymMatrixMap;
   579           
   580       ///Constructor.
   581       FirstKeyProxy(DynamicAsymMatrixMap& _map) : _owner(_map) { }
   582     protected:
   583 
   584       ///\brief Add a new FirstKey to the map.
   585       ///
   586       ///It adds a new FirstKey to the map. It is called by the
   587       ///observer notifier and it is ovverride the add() virtual
   588       ///member function in the observer base. It will call the
   589       ///maps addFirstKey() function.
   590       virtual void add(const FirstKey& _firstKey){
   591         _owner.addFirstKey(_firstKey);
   592       }
   593           
   594       ///\brief Add more new FirstKey to the map.
   595       ///
   596       ///It adds more new FirstKey to the map. It is called by the
   597       ///observer notifier and it is ovverride the add() virtual
   598       ///member function in the observer base. It will call the
   599       ///map's addFirstKeys() function.
   600       virtual void add(const std::vector<FirstKey>& _firstKeys){
   601         _owner.addFirstKeys(_firstKeys);
   602       }
   603           
   604       ///\brief Erase a FirstKey from the map.
   605       ///
   606       ///Erase a FirstKey from the map. It called by the observer
   607       ///notifier and it overrides the erase() virtual member
   608       ///function of the observer base. It will call the map's
   609       ///eraseFirstKey() function.
   610       virtual void erase(const FirstKey& _firstKey){
   611         _owner.eraseFirstKey(_firstKey);
   612       }
   613           
   614       ///\brief Erase more FirstKey from the map.
   615       ///
   616       ///Erase more FirstKey from the map. It called by the
   617       ///observer notifier and it overrides the erase() virtual
   618       ///member function of the observer base. It will call the
   619       ///map's eraseFirstKeys() function.
   620       virtual void erase(const std::vector<FirstKey>& _firstKeys){
   621         _owner.eraseFirstKeys(_firstKeys);
   622       }
   623           
   624       ///\brief Builds the map.
   625       ///
   626       ///It buildes the map. It called by the observer notifier
   627       ///and it overrides the build() virtual member function of
   628       ///the observer base.  It will call the map's build()
   629       ///function.
   630       virtual void build() {
   631         _owner.build();
   632         //_owner.buildFirst();
   633       }
   634           
   635       ///\brief Clear the map.
   636       ///
   637       ///It erases all items from the map. It called by the
   638       ///observer notifier and it overrides the clear() virtual
   639       ///memeber function of the observer base. It will call the
   640       ///map's clear() function.
   641       virtual void clear() {
   642         _owner.clear();
   643         //_owner.clearFirst();
   644       }
   645     private:
   646           
   647       ///The map type for it is linked.
   648       DynamicAsymMatrixMap& _owner;
   649     };//END OF FIRSTKEYPROXY
   650       
   651       ///\brief Proxy class for the second key type.
   652       ///
   653       ///The proxy class belongs to the SecondKey type. It is
   654       ///necessary because if one want use the same conatainer types
   655       ///and same nested types but on other instances of containers
   656       ///than due to the type equiality of nested types it requires a
   657       ///proxy mechanism.
   658     class SecondKeyProxy
   659       : protected 
   660     ItemSetTraits<_SecondContainer, _SecondContainerItem>::
   661     ItemNotifier::ObserverBase {
   662         
   663     public:
   664 
   665       friend class DynamicAsymMatrixMap;
   666       ///Constructor.
   667       SecondKeyProxy(DynamicAsymMatrixMap& _map) : _owner(_map) { }
   668 
   669     protected:
   670           
   671       ///\brief Add a new SecondKey to the map.
   672       ///
   673       ///It adds a new SecondKey to the map. It is called by the
   674       ///observer notifier and it is ovverride the add() virtual
   675       ///member function in the observer base. It will call the
   676       ///maps addSecondKey() function.
   677       virtual void add(const SecondKey& _secondKey){
   678         _owner.addSecondKey(_secondKey);
   679       }
   680     
   681       ///\brief Add more new SecondKey to the map.
   682       ///
   683       ///It adds more new SecondKey to the map. It is called by
   684       ///the observer notifier and it is ovverride the add()
   685       ///virtual member function in the observer base. It will
   686       ///call the maps addSecondKeys() function.
   687       virtual void add(const std::vector<SecondKey>& _secondKeys){
   688         _owner.addSecondKeys(_secondKeys);
   689       }
   690           
   691       ///\brief Erase a SecondKey from the map.
   692       ///
   693       ///Erase a SecondKey from the map. It called by the observer
   694       ///notifier and it overrides the erase() virtual member
   695       ///function of the observer base. It will call the map's
   696       ///eraseSecondKey() function.
   697       virtual void erase(const SecondKey& _secondKey){
   698         _owner.eraseSecondKey(_secondKey);
   699       }
   700           
   701       ///\brief Erase more SecondKeys from the map.
   702       ///
   703       ///Erase more SecondKey from the map. It called by the
   704       ///observer notifier and it overrides the erase() virtual
   705       ///member function of the observer base. It will call the
   706       ///map's eraseSecondKeys() function.
   707       virtual void erase(const std::vector<SecondKey>& _secondKeys){
   708         _owner.eraseSecondKeys(_secondKeys);
   709       }
   710           
   711       ///\brief Builds the map.
   712       ///
   713       ///It buildes the map. It called by the observer notifier
   714       ///and it overrides the build() virtual member function of
   715       ///the observer base.  It will call the map's build()
   716       ///function.
   717       virtual void build() {
   718         _owner.build();
   719       }
   720           
   721       ///\brief Clear the map.
   722       ///
   723       ///It erases all items from the map. It called by the
   724       ///observer notifier and it overrides the clear() virtual
   725       ///memeber function of the observer base. It will call the
   726       ///map's clear() function.
   727       virtual void clear() {
   728         _owner.clear();
   729         //_owner.clearFirst();
   730       }
   731     private:
   732           
   733       ///The type of map for which it is attached.
   734       DynamicAsymMatrixMap& _owner;
   735     };//END OF SECONDKEYPROXY
   736       
   737   private:
   738     
   739     /// \e
   740     typedef std::vector<Value> Container;
   741       
   742     ///The type of constainer which stores the values of the map.
   743     typedef std::vector<Container> DContainer;
   744 
   745     ///The std:vector type which contains the data
   746     DContainer values;
   747       
   748     ///Member for the first proxy class
   749     FirstKeyProxy _first_key_proxy;
   750       
   751     ///Member for the second proxy class
   752     SecondKeyProxy _second_key_proxy;
   753 
   754   public:
   755     
   756     ///The refernce type of the map.
   757     typedef typename Container::reference Reference;
   758       
   759     ///The const reference type of the constainer.
   760     typedef typename Container::const_reference ConstReference;
   761 
   762     ///\brief Constructor what create the map for the two containers type.
   763     ///
   764     ///Creates the matrix map and initialize the values with Value()
   765     DynamicAsymMatrixMap(const _FirstContainer& _firstContainer, 
   766                   const _SecondContainer& _secondContainer)
   767       : values(DContainer(_firstContainer.maxId(FirstKey())+1,
   768                           Container(_secondContainer.maxId(SecondKey())+1))),
   769         _first_key_proxy(*this),
   770         _second_key_proxy(*this)
   771     {
   772       _first_key_proxy.attach(_firstContainer.getNotifier(FirstKey()));
   773       _second_key_proxy.attach(_secondContainer.getNotifier(SecondKey()));
   774     }
   775 
   776     ///\brief Constructor what create the map for the two containers type.
   777     ///
   778     ///Creates the matrix map and initialize the values with the given _value
   779     DynamicAsymMatrixMap(const _FirstContainer& _firstContainer, 
   780                   const _SecondContainer& _secondContainer, 
   781                   const Value& _value)
   782       : values(DContainer(_firstContainer.maxId(FirstKey())+1,
   783                           Container(_secondContainer.maxId(SecondKey())+1,
   784                                     _value))),
   785         _first_key_proxy(*this),
   786         _second_key_proxy(*this)
   787     {
   788       _first_key_proxy.attach(_firstContainer.getNotifier(FirstKey()));
   789       _second_key_proxy.attach(_secondContainer.getNotifier(SecondKey()));
   790     }
   791       
   792     ///\brief Copy constructor.
   793     ///
   794     ///The copy constructor of the map.
   795     DynamicAsymMatrixMap(const DynamicAsymMatrixMap& _copy) 
   796       : _first_key_proxy(*this), _second_key_proxy(*this) {
   797       if(_copy._first_key_proxy.attached() && 
   798          _copy._second_key_proxy.attached()){
   799         _first_key_proxy.attach(*_copy._first_key_proxy.getNotifier());
   800         _second_key_proxy.attach(*_copy._second_key_proxy.getNotifier());
   801         values = _copy.values;
   802       }
   803     }
   804       
   805     ///\brief Destructor
   806     ///
   807     ///Destructor what detach() from the attached objects.  May this
   808     ///function is not necessary because the destructor of
   809     ///ObserverBase do the same.
   810     ~DynamicAsymMatrixMap() {
   811       if(_first_key_proxy.attached()){
   812         _first_key_proxy.detach();
   813       }
   814       if(_second_key_proxy.attached()){
   815         _second_key_proxy.detach();
   816       }
   817     }
   818       
   819     ///\brief Gives back the value assigned to the \c first - \c
   820     ///second ordered pair.
   821     ///
   822     ///Gives back the value assigned to the \c first - \c second
   823     ///ordered pair.
   824     Reference operator()(const FirstKey& _first, const SecondKey& _second) {
   825       return values[_first_key_proxy.getNotifier()->id(_first)]
   826         [_second_key_proxy.getNotifier()->id(_second)];
   827     }
   828 
   829     ///\brief Gives back the value assigned to the \c first - \c
   830     ///second ordered pair.
   831     ///
   832     ///Gives back the value assigned to the \c first - \c second
   833     ///ordered pair.
   834     ConstReference operator()(const FirstKey& _first, 
   835                               const SecondKey& _second) const {
   836       return values[_first_key_proxy.getNotifier()->id(_first)]
   837         [_second_key_proxy.getNotifier()->id(_second)];
   838     }
   839 
   840     ///\brief Setter function for this matrix map.
   841     ///
   842     ///Setter function for this matrix map.
   843     void set(const FirstKey& first, const SecondKey& second, 
   844              const Value& value){
   845       values[_first_key_proxy.getNotifier()->id(first)]
   846         [_second_key_proxy.getNotifier()->id(second)] = value;
   847     }
   848 
   849     ///\brief The assignement operator.
   850     ///
   851     ///It allow to assign a map to an other. It
   852     DynamicAsymMatrixMap& operator=(const DynamicAsymMatrixMap& _cmap){
   853       return operator=<DynamicAsymMatrixMap>(_cmap);
   854     }
   855       
   856     ///\brief Template assignement operator.
   857     ///
   858     ///It copy the element of the given map to its own container.  The
   859     ///type of the two map shall be the same.
   860     template <typename CMap>
   861     DynamicAsymMatrixMap& operator=(const CMap& _cdmap){
   862       checkConcept<concept::ReadMatrixMap<FirstKey, SecondKey, Value>, CMap>();
   863       const typename FirstKeyProxy::Notifier* notifierFirstKey = 
   864         _first_key_proxy.getNotifier();
   865       const typename SecondKeyProxy::Notifier* notifierSecondKey = 
   866         _second_key_proxy.getNotifier();
   867       FirstKey itemFirst;
   868       SecondKey itemSecond;
   869       for(notifierFirstKey->first(itemFirst); itemFirst != INVALID; 
   870           notifierFirstKey->next(itemFirst)){
   871         for(notifierSecondKey->first(itemSecond); itemSecond != INVALID; 
   872             notifierSecondKey->next(itemSecond)){
   873           set(itemFirst, itemSecond, _cdmap(itemFirst,itemSecond));
   874         }
   875       }
   876       return *this;
   877     }
   878       
   879   protected:
   880     
   881     ///\brief Add a new FirstKey to the map.
   882     ///
   883     ///It adds a new FirstKey to the map. It is called by the observer
   884     ///class belongs to the FirstKey type.
   885     void addFirstKey(const FirstKey& firstKey) {
   886       int size = (int)values.size();
   887       if( _first_key_proxy.getNotifier()->id(firstKey)+1 >= size ){
   888         values.resize(_first_key_proxy.getNotifier()->id(firstKey)+1);
   889         if( (int)values[0].size() != 0 ){
   890           int innersize = (int)values[0].size();
   891           for(int i=size; i!=(int)values.size();++i){
   892             (values[i]).resize(innersize);
   893           }
   894         }else if(_second_key_proxy.getNotifier()->maxId() >= 0){
   895           int innersize = _second_key_proxy.getNotifier()->maxId();
   896           for(int i = 0; i != (int)values.size(); ++i){
   897             values[0].resize(innersize);
   898           }
   899         }
   900       }
   901     }
   902 
   903     ///\brief Adds more new FirstKeys to the map.
   904     ///
   905     ///It adds more new FirstKeys to the map. It called by the
   906     ///observer class belongs to the FirstKey type.
   907     void addFirstKeys(const std::vector<FirstKey>& firstKeys){
   908       int max = values.size() - 1;
   909       for(int i=0; i != (int)firstKeys.size(); ++i){
   910         int id = _first_key_proxy.getNotifier()->id(firstKeys[i]);
   911         if(max < id){
   912           max = id;
   913         }
   914       }
   915       int size = (int)values.size();
   916       if(max >= size){
   917         values.resize(max + 1);
   918         if( (int)values[0].size() != 0){
   919           int innersize = (int)values[0].size();
   920           for(int i = size; i != (max + 1); ++i){
   921             values[i].resize(innersize);
   922           }
   923         }else if(_second_key_proxy.getNotifier()->maxId() >= 0){
   924           int innersize = _second_key_proxy.getNotifier()->maxId();
   925           for(int i = 0; i != (int)values.size(); ++i){
   926             values[i].resize(innersize);
   927           }
   928         }
   929       }
   930     }
   931 
   932     ///\brief Add a new SecondKey to the map.
   933     ///
   934     ///It adds a new SecondKey to the map. It is called by the
   935     ///observer class belongs to the SecondKey type.
   936     void addSecondKey(const SecondKey& secondKey) {
   937       if(values.size() == 0){
   938         return;
   939       }
   940       int id = _second_key_proxy.getNotifier()->id(secondKey);
   941       if(id >= (int)values[0].size()){
   942         for(int i=0;i!=(int)values.size();++i){
   943           values[i].resize(id+1);
   944         }
   945       }
   946     }
   947         
   948     ///\brief Adds more new SecondKeys to the map.
   949     ///
   950     ///It adds more new SecondKeys to the map. It called by the
   951     ///observer class belongs to the SecondKey type.
   952     void addSecondKeys(const std::vector<SecondKey>& secondKeys){
   953       if(values.size() == 0){
   954         return;
   955       }
   956       int max = values[0].size();
   957       for(int i = 0; i != (int)secondKeys.size(); ++i){
   958         int id = _second_key_proxy.getNotifier()->id(secondKeys[i]);
   959         if(max < id){
   960           max = id;
   961         }
   962       }
   963       if(max > (int)values[0].size()){
   964         for(int i = 0; i != (int)values.size(); ++i){
   965           values[i].resize(max + 1);
   966         }
   967       }
   968     }
   969     
   970     ///\brief Erase a FirstKey from the map.
   971     ///
   972     ///Erase a FirstKey from the map. It called by the observer
   973     ///class belongs to the FirstKey type.
   974     void eraseFirstKey(const FirstKey& first) {
   975       int id = _first_key_proxy.getNotifier()->id(first);
   976       for(int i = 0; i != (int)values[id].size(); ++i){
   977         values[id][i] = Value();
   978       }
   979     }
   980         
   981     ///\brief Erase more FirstKey from the map.
   982     ///
   983     ///Erase more FirstKey from the map. It called by the observer
   984     ///class belongs to the FirstKey type.
   985     void eraseFirstKeys(const std::vector<FirstKey>& firstKeys) {
   986       for(int j = 0; j != (int)firstKeys.size(); ++j){
   987         int id = _first_key_proxy.getNotifier()->id(firstKeys[j]);
   988         for(int i = 0; i != (int)values[id].size(); ++i){
   989           values[id][i] = Value();
   990         }
   991       }
   992     }
   993 
   994     ///\brief Erase a SecondKey from the map.
   995     ///
   996     ///Erase a SecondKey from the map. It called by the observer class
   997     ///belongs to the SecondKey type.
   998     void eraseSecondKey(const SecondKey& second) {
   999       if(values.size() == 0){
  1000         return;
  1001       }
  1002       int id = _second_key_proxy.getNotifier()->id(second);
  1003       for(int i = 0; i != (int)values.size(); ++i){
  1004         values[i][id] = Value();
  1005       }
  1006     }
  1007         
  1008     ///\brief Erase more SecondKey from the map.
  1009     ///
  1010     ///Erase more SecondKey from the map. It called by the observer
  1011     ///class belongs to the SecondKey type.
  1012     void eraseSecondKeys(const std::vector<SecondKey>& secondKeys) {
  1013       if(values.size() == 0){
  1014         return;
  1015       }
  1016       for(int j = 0; j != (int)secondKeys.size(); ++j){
  1017         int id = _second_key_proxy.getNotifier()->id(secondKeys[j]);
  1018         for(int i = 0; i != (int)values.size(); ++i){
  1019           values[i][id] = Value();
  1020         }
  1021       }
  1022     }
  1023 
  1024     ///\brief Builds the map.
  1025     ///
  1026     ///It buildes the map. It is called by the observer class belongs
  1027     ///to the FirstKey or SecondKey type.
  1028     void build() {
  1029       values.resize(_first_key_proxy.getNotifier()->maxId());
  1030       for(int i=0; i!=(int)values.size(); ++i){
  1031         values[i].resize(_second_key_proxy.getNotifier()->maxId());
  1032       }
  1033     }
  1034     
  1035     ///\brief Clear the map.
  1036     ///
  1037     ///It erases all items from the map. It is called by the observer class
  1038     ///belongs to the FirstKey or SecondKey type.
  1039     void clear() {
  1040       for(int i=0; i!=(int)values.size(); ++i) {
  1041         values[i].clear();
  1042       }
  1043       values.clear();
  1044     }
  1045  
  1046   };
  1047 
  1048 
  1049 
  1050 }
  1051 
  1052 #endif