# HG changeset patch # User deba # Date 1128592701 0 # Node ID 4fb435ad31cfc0c9ccc381536b4dbbc338077d61 # Parent 1d09b48e8d550962e86b6f2b10e226d0ef934f73 Little modifications diff -r 1d09b48e8d55 -r 4fb435ad31cf doc/adaptor_references.dox --- a/doc/adaptor_references.dox Thu Oct 06 09:57:23 2005 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,170 +0,0 @@ -namespace lemon { -/*! - -\page adaptor-references Smart Reference Handling - -The adaptor classes are very useful tools in the lemon library. It makes -possible to create various data view of the current data structures without -of the copy of them. This makes the lemon programming efficient and -consederably fast. - -\section problem The problem - -The adaptors usually use references or pointers to reference to an -existing data structure. We may use an algorithm in the following way: -\code -function_algorithm(adaptor(structure)); -\endcode - -But what about the class algorithms: -\code -class_algorithm alg; -alg.add(adaptor(structure)); -alg.run(); -\endcode -The algorithm store a reference to the given structure. It is a created -as temporarly and when the expression of the \c add() function is evaluated it -will be destructed. It is very dangerous handling of the adaptors. - -\section solution The solution - -We made reference to a temporarly constructed adaptor but we should make -a copy of the adaptor when it is given as parameter to a class. -It is not impossible with a little tranformation of the code. - -Let's first create some helper class: -\code -template -struct SmartConstReference { - typedef const _Type& Type; -}; - -template -struct SmartConstReference< - _Type, - typename enable_if::type -> { - typedef const _Type Type; -}; -\endcode -Then we can place NeedCopy tags in the adaptor classes: -\code -template -class AddMap { - typename SmartConstReference::Type m1; - typename SmartConstReference::Type m2; - -public: - - typedef True NeedCopy; - - typedef typename M1::Key Key; - typedef typename M1::Value Value; - - AddMap(const M1 &_m1,const M2 &_m2) : m1(_m1), m2(_m2) {}; - Value operator[](Key k) const {return m1[k]+m2[k];} -}; -\endcode -Then we can transform all of the template map and graph references to -\c SmartConstReference::Type or \c SmartConstReference::Type. -This way we copy all of maps and graphs what we should copy but the -greater data structures are not copied. - -\section not-const If the adaptor is not const -The solution is very similar but it gives an additional problem. -We make the same \c SmartReferences: -\code -template -struct SmartReference { - typedef _Type& Type; -}; - -template -struct SmartReference< - _Type, - typename enable_if::type -> { - typedef _Type Type; -}; -\endcode -Let's create a class that use it: -\code -template -class Algorithm { -public: - SmartReference::Type map; - Algorithm(Map& _map) : map(_map) {} - ... -}; -\endcode -But if we want to give an adaptor function as parameter -it will be a compile error. The adaptor will be created as temporarly -so it cannot give as reference just as const reference. - -Make more helper class: -\code -template -struct SmartParameter { - typedef _Type& Type; -}; - -template -struct SmartParameter< - _Type, - typename enable_if::type -> { - typedef const _Type& Type; -}; -\endcode -And the repaired code: -\code -template -class Algorithm { -public: - SmartReference::Type map; - Algorithm(SmartParameter::Type _map) : map(_map) {} - ... -}; -\endcode -But some times it does not help: -\code -class Algorithm { -public: - ... - - template - void addMap(SmartParameter::Type _map) { - ... - } - ... -}; -\endcode -Actually, it is a good code but the template parameter should -be written because it cannot be found out from the parameter type. -This can be solved with a bigger transformation: -\code -class Algorithm { -public: - ... - - template - void addMap(const Map& _map) { - _addMap::Type, Map>(_map); - } - template - void addMap(const Map& _map) { - _addMap::Type, Map>(_map); - } - -private: - template - void _addMap(MapParameter _map) { - ... - } - ... -}; -\endcode -This way we solved the smart referencing problem. -\author Balazs Dezso -*/ -} diff -r 1d09b48e8d55 -r 4fb435ad31cf lemon/graph_utils.h --- a/lemon/graph_utils.h Thu Oct 06 09:57:23 2005 +0000 +++ b/lemon/graph_utils.h Thu Oct 06 09:58:21 2005 +0000 @@ -1400,7 +1400,7 @@ } void add(const Node& node) { - if (size(graph.id(node) + 1) > values.size()) { + if (size(graph.id(node) + 1) >= (int)values.size()) { values.resize(size(graph.id(node) + 1)); } } diff -r 1d09b48e8d55 -r 4fb435ad31cf test/graph_test.cc --- a/test/graph_test.cc Thu Oct 06 09:57:23 2005 +0000 +++ b/test/graph_test.cc Thu Oct 06 09:58:21 2005 +0000 @@ -7,6 +7,7 @@ #include #include #include +#include #include "test_tools.h" #include "graph_test.h" @@ -59,6 +60,9 @@ { // checking full graph checkConcept(); } + { // checking full graph + checkConcept(); + } std::cout << __FILE__ ": All tests passed.\n";