Tulip  4.6.0
Better Visualization Through Research
library/tulip-core/include/tulip/vectorgraphproperty.h
00001 /*
00002  *
00003  * This file is part of Tulip (www.tulip-software.org)
00004  *
00005  * Authors: David Auber and the Tulip development Team
00006  * from LaBRI, University of Bordeaux
00007  *
00008  * Tulip is free software; you can redistribute it and/or modify
00009  * it under the terms of the GNU Lesser General Public License
00010  * as published by the Free Software Foundation, either version 3
00011  * of the License, or (at your option) any later version.
00012  *
00013  * Tulip is distributed in the hope that it will be useful,
00014  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00015  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
00016  * See the GNU General Public License for more details.
00017  *
00018  */
00019 ///@cond DOXYGEN_HIDDEN
00020 
00021 #ifndef VECTORGRAPHPROPERTY_H
00022 #define VECTORGRAPHPROPERTY_H
00023 #include <algorithm>
00024 
00025 namespace tlp {
00026 class VectorGraph;
00027 /**
00028  * @brief Internal class to access to a stl::vector in VectorGraph
00029  * @warning never use that class
00030  */
00031 class ValArrayInterface {
00032   friend class VectorGraph;
00033 protected:
00034   virtual void addElement(const unsigned int id) = 0;
00035   virtual void reserve(const size_t size) = 0;
00036   virtual ~ValArrayInterface() {}
00037 };
00038 //===========================================
00039 /**
00040  * @brief Internal class to access to a stl::vector in VectorGraph
00041  * @warning never use that class
00042  */
00043 template <typename TYPE>
00044 class  ValArray : public  ValArrayInterface {
00045   friend class VectorGraph;
00046 protected:
00047   ValArray(const unsigned int size = 0, const unsigned int capacity = 0) {
00048     _data.reserve(capacity);
00049     _data.resize(size);
00050   }
00051   virtual ~ValArray() {}
00052   void addElement(const unsigned int id) {
00053     if (id >= _data.size()) {
00054       _data.resize(id);
00055       _data.push_back(TYPE());
00056     }
00057   }
00058   void reserve(const size_t size) {
00059     _data.reserve(size);
00060   }
00061 
00062 public:
00063   std::vector<TYPE> _data; /**< TODO */
00064 };
00065 /**
00066   * @class VectorGraphProperty
00067   * @brief That class enables to factorize code for NodeProperty and EdgeProperty in VectorGraph, it could not be used directly.
00068   * @see NodeProperty
00069   * @see EdgeProperty
00070   * @see VectorGraph
00071   */
00072 template <typename TYPE>
00073 class VectorGraphProperty {
00074   friend class VectorGraph;
00075 public:
00076   /**
00077     * @brief read/write accessor
00078     *
00079     * return the value of the ith element and enables to modify it.
00080     */
00081   typename std::vector<TYPE>::reference operator[](const size_t id) {
00082     //assert(isValid());
00083     assert(id < (*_array)._data.size());
00084     return (*_array)._data[id];
00085   }
00086   /**
00087     * @brief read accessor
00088     *
00089     * return the value of the ith element.
00090     */
00091   typename std::vector<TYPE>::const_reference operator[](const size_t id) const {
00092     //assert(isValid());
00093     assert(id < (*_array)._data.size());
00094     return (*_array)._data[id];
00095   }
00096   /**
00097     * @bried Set all the value of the property to the value given in parameter
00098     *
00099     * That function affect the same value to all elements of the vector, there
00100     * is no effect on the future value added in the vector
00101     * @warning There is differences between the setAll of the MutableContainer and
00102     * the setAll of VectorProperty (NodeProperty or EdgeProperty). The MutableContainer,
00103     * ensures that new inserted element will have the value given by the last setAll
00104     *
00105     * @see MutableContainer
00106     */
00107   void setAll(const TYPE &obj) {
00108     fill(_array->_data.begin(), _array->_data.end(), obj);
00109   }
00110   /**
00111     * @brief write accessor
00112     *
00113     * change the value of the ith element.
00114     */
00115   void set(const size_t id, const TYPE &obj) {
00116     (*this)[id] = obj;
00117   }
00118   /**
00119     * @brief read accessor
00120     *
00121     * return the value of the ith element.
00122     */
00123   typename std::vector<TYPE>::const_reference get(const size_t id) const {
00124     return (*this)[id];
00125   }
00126 #ifndef NDEBUG
00127   virtual bool isValid() const = 0;
00128 #endif
00129 
00130 protected:
00131   VectorGraphProperty():_array(0), _graph(0) {
00132   }
00133   VectorGraphProperty(const VectorGraphProperty &obj): _array(obj._array), _graph(obj._graph) {
00134   }
00135   VectorGraphProperty(ValArray<TYPE> *array, VectorGraph *graph):_array(array), _graph(graph) {
00136   }
00137 protected:
00138   ValArray<TYPE> *_array; /**< TODO */
00139   VectorGraph *_graph; /**< TODO */
00140 };
00141 
00142 /**
00143  * @class EdgeProperty
00144  * @brief That class enables to define a property/attribute on edges on a VectorGraph.
00145  *
00146  * Using EdgeProperty you can assign any kind of attribute to edges. To use that class
00147  * you must first create an instance of EdgeProperty and then connect it to your graph.
00148  * NodeProperty can be copied in another EdgeProperty, however the to NodeProperty will
00149  * share the same content. You can consider that EdgeProperty is just a pointer on a stl:vector.
00150  * to free memory used by a EdgeProperty connected to a graph you must use the free function.
00151  * @warning After the call to free all The copy of the orignal EdgeProperty are no more valid
00152  *
00153  * Using EdgeProperty you can store and access to values with the same efficiency as if
00154  * you created manually a vector. EdgeProperty manage for you the resize, etc... when the
00155  * graph is modified.
00156  *
00157  * Furthemrore, in DEBUG mode, operator[] check if one try to access outside of the Array Bound.
00158  * in DEBUG mode, the validy of the Property is also checked (if it has been free/alloc etc...)
00159  *
00160  * @code
00161  * VectorGraph g;
00162  * EdgeProperty<double> weight;
00163  * g.alloc(weight); //connect weight to g, g allocate memory for that attribute
00164  * edge e;
00165  * forEach(e, g.getEdges()) {
00166  *   weight[n] = g.deg(g.target(e)) + g.deg(g.source(e));
00167  * }
00168  * EdgeProperty<double> weight2 = weight; //weight2 and weight are pointing on the same memory addres
00169  * weight2[g[0]] = 3;
00170  * tlp::debug() << weight[g[0]]; //output 3
00171  * g.free(weight2); //free the memory, weight and weight2 are no more valid.
00172  * @endcode
00173  * @see VectorGraph alloc(EdgeProperty)
00174  * @see VectorGraph free(EdgeProperty)
00175  * @see VectorGraph
00176  */
00177 template <typename TYPE>
00178 class EdgeProperty : public VectorGraphProperty<TYPE> {
00179   friend class VectorGraph;
00180 public:
00181   EdgeProperty():VectorGraphProperty<TYPE>() {}
00182   EdgeProperty(const EdgeProperty &obj): VectorGraphProperty<TYPE>(obj) {}
00183 #ifndef NDEBUG
00184   bool isValid() const;
00185 #endif
00186 
00187 private:
00188   EdgeProperty(ValArray<TYPE> *array, VectorGraph *graph):VectorGraphProperty<TYPE>(array, graph) {}
00189 
00190 };
00191 /**
00192   * @class NodeProperty
00193   * @brief That class enables to define a property/attribute on nodes on a VectorGraph.
00194   *
00195   * Using NodeProperty you can assign any kind of attribute to nodes. To use that class
00196   * you must first create an instance of NodeProperty and then connect it to your graph.
00197   * NodeProperty can be copied in another NodeProperty, however the to NodeProperty will
00198   * share the same content. You can consider that NodeProperty is just a pointer on a stl:vector.
00199   * to free memory used by a NodeProperty connected to a graph you must use the free function.
00200   * @warning After the call to free all The copy of the orignal NodeProperty are no more valid
00201   *
00202   * Using NodeProperty you can store and access to values with the same efficiency as if
00203   * you created manually a vector. NodeProperty manage for you the resize, etc... when the
00204   * graph is modified.
00205   *
00206   * Furthemrore, in DEBUG mode, operator[] check if one try to access outside of the Array Bound.
00207   * in DEBUG mode, the validy of the Property is also checked (if it has been free/alloc etc...)
00208   *
00209   * @code
00210   * VectorGraph g;
00211   * NodeProperty<double> weight;
00212   * g.alloc(weight); //connect weight to g, g allocate memory for that attribute
00213   * node n;
00214   * forEach(n, g.getNodes()) {
00215   *   weight[n] = g.deg(n);
00216   * }
00217   * NodeProperty<double> weight2 = weight; //weight2 and weight are pointing on the same memory addres
00218   * weight2[g[0]] = 3;
00219   * tlp::debug() << weight[g[0]]; //output 3
00220   * g.free(weight2); //free the memory, weight and weight2 are no more valid.
00221   * @endcode
00222   * @see VectorGraph alloc(NodeProperty)
00223   * @see VectorGraph free(NodeProperty)
00224   */
00225 template <typename TYPE>
00226 class NodeProperty : public VectorGraphProperty<TYPE> {
00227   friend class VectorGraph;
00228 public:
00229   NodeProperty():VectorGraphProperty<TYPE>() {}
00230   NodeProperty(const NodeProperty &obj): VectorGraphProperty<TYPE>(obj) {}
00231 #ifndef NDEBUG
00232   bool isValid() const;
00233 #endif
00234 
00235 private:
00236   NodeProperty(ValArray<TYPE> *array, VectorGraph *graph):VectorGraphProperty<TYPE>(array, graph) {}
00237 };
00238 
00239 }
00240 #endif // VECTORGRAPHPROPERTY_H
00241 ///@endcond
 All Classes Files Functions Variables Enumerations Enumerator Properties