Changes in lemon/bits/alteration_notifier.h [236:da953e387d31:314:2cc60866a0c9] in lemon-1.2
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
lemon/bits/alteration_notifier.h
r236 r314 25 25 #include <lemon/core.h> 26 26 27 // /\ingroup graphbits28 // /\file29 // /\brief Observer notifier for graph alteration observers.27 //\ingroup graphbits 28 //\file 29 //\brief Observer notifier for graph alteration observers. 30 30 31 31 namespace lemon { 32 32 33 /// \ingroup graphbits 34 /// 35 /// \brief Notifier class to notify observes about alterations in 36 /// a container. 37 /// 38 /// The simple graph's can be refered as two containers, one node container 39 /// and one edge container. But they are not standard containers they 40 /// does not store values directly they are just key continars for more 41 /// value containers which are the node and edge maps. 42 /// 43 /// The graph's node and edge sets can be changed as we add or erase 44 /// nodes and edges in the graph. LEMON would like to handle easily 45 /// that the node and edge maps should contain values for all nodes or 46 /// edges. If we want to check on every indicing if the map contains 47 /// the current indicing key that cause a drawback in the performance 48 /// in the library. We use another solution we notify all maps about 49 /// an alteration in the graph, which cause only drawback on the 50 /// alteration of the graph. 51 /// 52 /// This class provides an interface to the container. The \e first() and \e 53 /// next() member functions make possible to iterate on the keys of the 54 /// container. The \e id() function returns an integer id for each key. 55 /// The \e maxId() function gives back an upper bound of the ids. 56 /// 57 /// For the proper functonality of this class, we should notify it 58 /// about each alteration in the container. The alterations have four type 59 /// as \e add(), \e erase(), \e build() and \e clear(). The \e add() and 60 /// \e erase() signals that only one or few items added or erased to or 61 /// from the graph. If all items are erased from the graph or from an empty 62 /// graph a new graph is builded then it can be signaled with the 63 /// clear() and build() members. Important rule that if we erase items 64 /// from graph we should first signal the alteration and after that erase 65 /// them from the container, on the other way on item addition we should 66 /// first extend the container and just after that signal the alteration. 67 /// 68 /// The alteration can be observed with a class inherited from the 69 /// \e ObserverBase nested class. The signals can be handled with 70 /// overriding the virtual functions defined in the base class. The 71 /// observer base can be attached to the notifier with the 72 /// \e attach() member and can be detached with detach() function. The 73 /// alteration handlers should not call any function which signals 74 /// an other alteration in the same notifier and should not 75 /// detach any observer from the notifier. 76 /// 77 /// Alteration observers try to be exception safe. If an \e add() or 78 /// a \e clear() function throws an exception then the remaining 79 /// observeres will not be notified and the fulfilled additions will 80 /// be rolled back by calling the \e erase() or \e clear() 81 /// functions. Thence the \e erase() and \e clear() should not throw 82 /// exception. Actullay, it can be throw only 83 /// \ref AlterationObserver::ImmediateDetach ImmediateDetach 84 /// exception which detach the observer from the notifier. 85 /// 86 /// There are some place when the alteration observing is not completly 87 /// reliable. If we want to carry out the node degree in the graph 88 /// as in the \ref InDegMap and we use the reverseEdge that cause 89 /// unreliable functionality. Because the alteration observing signals 90 /// only erasing and adding but not the reversing it will stores bad 91 /// degrees. The sub graph adaptors cannot signal the alterations because 92 /// just a setting in the filter map can modify the graph and this cannot 93 /// be watched in any way. 94 /// 95 /// \param _Container The container which is observed. 96 /// \param _Item The item type which is obserbved. 33 // \ingroup graphbits 34 // 35 // \brief Notifier class to notify observes about alterations in 36 // a container. 37 // 38 // The simple graph's can be refered as two containers, one node container 39 // and one edge container. But they are not standard containers they 40 // does not store values directly they are just key continars for more 41 // value containers which are the node and edge maps. 42 // 43 // The graph's node and edge sets can be changed as we add or erase 44 // nodes and edges in the graph. LEMON would like to handle easily 45 // that the node and edge maps should contain values for all nodes or 46 // edges. If we want to check on every indicing if the map contains 47 // the current indicing key that cause a drawback in the performance 48 // in the library. We use another solution we notify all maps about 49 // an alteration in the graph, which cause only drawback on the 50 // alteration of the graph. 51 // 52 // This class provides an interface to the container. The \e first() and \e 53 // next() member functions make possible to iterate on the keys of the 54 // container. The \e id() function returns an integer id for each key. 55 // The \e maxId() function gives back an upper bound of the ids. 56 // 57 // For the proper functonality of this class, we should notify it 58 // about each alteration in the container. The alterations have four type 59 // as \e add(), \e erase(), \e build() and \e clear(). The \e add() and 60 // \e erase() signals that only one or few items added or erased to or 61 // from the graph. If all items are erased from the graph or from an empty 62 // graph a new graph is builded then it can be signaled with the 63 // clear() and build() members. Important rule that if we erase items 64 // from graph we should first signal the alteration and after that erase 65 // them from the container, on the other way on item addition we should 66 // first extend the container and just after that signal the alteration. 67 // 68 // The alteration can be observed with a class inherited from the 69 // \e ObserverBase nested class. The signals can be handled with 70 // overriding the virtual functions defined in the base class. The 71 // observer base can be attached to the notifier with the 72 // \e attach() member and can be detached with detach() function. The 73 // alteration handlers should not call any function which signals 74 // an other alteration in the same notifier and should not 75 // detach any observer from the notifier. 76 // 77 // Alteration observers try to be exception safe. If an \e add() or 78 // a \e clear() function throws an exception then the remaining 79 // observeres will not be notified and the fulfilled additions will 80 // be rolled back by calling the \e erase() or \e clear() 81 // functions. Thence the \e erase() and \e clear() should not throw 82 // exception. Actullay, it can be throw only \ref ImmediateDetach 83 // exception which detach the observer from the notifier. 84 // 85 // There are some place when the alteration observing is not completly 86 // reliable. If we want to carry out the node degree in the graph 87 // as in the \ref InDegMap and we use the reverseEdge that cause 88 // unreliable functionality. Because the alteration observing signals 89 // only erasing and adding but not the reversing it will stores bad 90 // degrees. The sub graph adaptors cannot signal the alterations because 91 // just a setting in the filter map can modify the graph and this cannot 92 // be watched in any way. 93 // 94 // \param _Container The container which is observed. 95 // \param _Item The item type which is obserbved. 97 96 98 97 template <typename _Container, typename _Item> … … 105 104 typedef _Item Item; 106 105 107 // /\brief Exception which can be called from \e clear() and108 // /\e erase().109 // /110 // /From the \e clear() and \e erase() function only this111 // /exception is allowed to throw. The exception immediatly112 // /detaches the current observer from the notifier. Because the113 // /\e clear() and \e erase() should not throw other exceptions114 // /it can be used to invalidate the observer.106 // \brief Exception which can be called from \e clear() and 107 // \e erase(). 108 // 109 // From the \e clear() and \e erase() function only this 110 // exception is allowed to throw. The exception immediatly 111 // detaches the current observer from the notifier. Because the 112 // \e clear() and \e erase() should not throw other exceptions 113 // it can be used to invalidate the observer. 115 114 struct ImmediateDetach {}; 116 115 117 /// \brief ObserverBase is the base class for the observers. 118 /// 119 /// ObserverBase is the abstract base class for the observers. 120 /// It will be notified about an item was inserted into or 121 /// erased from the graph. 122 /// 123 /// The observer interface contains some pure virtual functions 124 /// to override. The add() and erase() functions are 125 /// to notify the oberver when one item is added or 126 /// erased. 127 /// 128 /// The build() and clear() members are to notify the observer 129 /// about the container is built from an empty container or 130 /// is cleared to an empty container. 131 116 // \brief ObserverBase is the base class for the observers. 117 // 118 // ObserverBase is the abstract base class for the observers. 119 // It will be notified about an item was inserted into or 120 // erased from the graph. 121 // 122 // The observer interface contains some pure virtual functions 123 // to override. The add() and erase() functions are 124 // to notify the oberver when one item is added or 125 // erased. 126 // 127 // The build() and clear() members are to notify the observer 128 // about the container is built from an empty container or 129 // is cleared to an empty container. 132 130 class ObserverBase { 133 131 protected: … … 136 134 friend class AlterationNotifier; 137 135 138 /// \brief Default constructor. 139 /// 140 /// Default constructor for ObserverBase. 141 /// 136 // \brief Default constructor. 137 // 138 // Default constructor for ObserverBase. 142 139 ObserverBase() : _notifier(0) {} 143 140 144 // /\brief Constructor which attach the observer into notifier.145 // /146 // /Constructor which attach the observer into notifier.141 // \brief Constructor which attach the observer into notifier. 142 // 143 // Constructor which attach the observer into notifier. 147 144 ObserverBase(AlterationNotifier& nf) { 148 145 attach(nf); 149 146 } 150 147 151 // /\brief Constructor which attach the obserever to the same notifier.152 // /153 // /Constructor which attach the obserever to the same notifier as154 // /the other observer is attached to.148 // \brief Constructor which attach the obserever to the same notifier. 149 // 150 // Constructor which attach the obserever to the same notifier as 151 // the other observer is attached to. 155 152 ObserverBase(const ObserverBase& copy) { 156 153 if (copy.attached()) { … … 159 156 } 160 157 161 // /\brief Destructor158 // \brief Destructor 162 159 virtual ~ObserverBase() { 163 160 if (attached()) { … … 166 163 } 167 164 168 /// \brief Attaches the observer into an AlterationNotifier. 169 /// 170 /// This member attaches the observer into an AlterationNotifier. 171 /// 165 // \brief Attaches the observer into an AlterationNotifier. 166 // 167 // This member attaches the observer into an AlterationNotifier. 172 168 void attach(AlterationNotifier& nf) { 173 169 nf.attach(*this); 174 170 } 175 171 176 /// \brief Detaches the observer into an AlterationNotifier. 177 /// 178 /// This member detaches the observer from an AlterationNotifier. 179 /// 172 // \brief Detaches the observer into an AlterationNotifier. 173 // 174 // This member detaches the observer from an AlterationNotifier. 180 175 void detach() { 181 176 _notifier->detach(*this); 182 177 } 183 178 184 /// \brief Gives back a pointer to the notifier which the map 185 /// attached into. 186 /// 187 /// This function gives back a pointer to the notifier which the map 188 /// attached into. 189 /// 179 // \brief Gives back a pointer to the notifier which the map 180 // attached into. 181 // 182 // This function gives back a pointer to the notifier which the map 183 // attached into. 190 184 Notifier* notifier() const { return const_cast<Notifier*>(_notifier); } 191 185 192 // /Gives back true when the observer is attached into a notifier.186 // Gives back true when the observer is attached into a notifier. 193 187 bool attached() const { return _notifier != 0; } 194 188 … … 202 196 typename std::list<ObserverBase*>::iterator _index; 203 197 204 // /\brief The member function to notificate the observer about an205 // /item is added to the container.206 // /207 // /The add() member function notificates the observer about an item208 // /is added to the container. It have to be overrided in the209 // /subclasses.198 // \brief The member function to notificate the observer about an 199 // item is added to the container. 200 // 201 // The add() member function notificates the observer about an item 202 // is added to the container. It have to be overrided in the 203 // subclasses. 210 204 virtual void add(const Item&) = 0; 211 205 212 // /\brief The member function to notificate the observer about213 // /more item is added to the container.214 // /215 // /The add() member function notificates the observer about more item216 // /is added to the container. It have to be overrided in the217 // /subclasses.206 // \brief The member function to notificate the observer about 207 // more item is added to the container. 208 // 209 // The add() member function notificates the observer about more item 210 // is added to the container. It have to be overrided in the 211 // subclasses. 218 212 virtual void add(const std::vector<Item>& items) = 0; 219 213 220 // /\brief The member function to notificate the observer about an221 // /item is erased from the container.222 // /223 // /The erase() member function notificates the observer about an224 // /item is erased from the container. It have to be overrided in225 // /the subclasses.214 // \brief The member function to notificate the observer about an 215 // item is erased from the container. 216 // 217 // The erase() member function notificates the observer about an 218 // item is erased from the container. It have to be overrided in 219 // the subclasses. 226 220 virtual void erase(const Item&) = 0; 227 221 228 // /\brief The member function to notificate the observer about229 // /more item is erased from the container.230 // /231 // /The erase() member function notificates the observer about more item232 // /is erased from the container. It have to be overrided in the233 // /subclasses.222 // \brief The member function to notificate the observer about 223 // more item is erased from the container. 224 // 225 // The erase() member function notificates the observer about more item 226 // is erased from the container. It have to be overrided in the 227 // subclasses. 234 228 virtual void erase(const std::vector<Item>& items) = 0; 235 229 236 /// \brief The member function to notificate the observer about the 237 /// container is built. 238 /// 239 /// The build() member function notificates the observer about the 240 /// container is built from an empty container. It have to be 241 /// overrided in the subclasses. 242 230 // \brief The member function to notificate the observer about the 231 // container is built. 232 // 233 // The build() member function notificates the observer about the 234 // container is built from an empty container. It have to be 235 // overrided in the subclasses. 243 236 virtual void build() = 0; 244 237 245 // /\brief The member function to notificate the observer about all246 // /items are erased from the container.247 // /248 // /The clear() member function notificates the observer about all249 // /items are erased from the container. It have to be overrided in250 // /the subclasses.238 // \brief The member function to notificate the observer about all 239 // items are erased from the container. 240 // 241 // The clear() member function notificates the observer about all 242 // items are erased from the container. It have to be overrided in 243 // the subclasses. 251 244 virtual void clear() = 0; 252 245 … … 263 256 public: 264 257 265 // /\brief Default constructor.266 // /267 // /The default constructor of the AlterationNotifier.268 // /It creates an empty notifier.258 // \brief Default constructor. 259 // 260 // The default constructor of the AlterationNotifier. 261 // It creates an empty notifier. 269 262 AlterationNotifier() 270 263 : container(0) {} 271 264 272 // /\brief Constructor.273 // /274 // /Constructor with the observed container parameter.265 // \brief Constructor. 266 // 267 // Constructor with the observed container parameter. 275 268 AlterationNotifier(const Container& _container) 276 269 : container(&_container) {} 277 270 278 // /\brief Copy Constructor of the AlterationNotifier.279 // /280 // /Copy constructor of the AlterationNotifier.281 // /It creates only an empty notifier because the copiable282 // /notifier's observers have to be registered still into that notifier.271 // \brief Copy Constructor of the AlterationNotifier. 272 // 273 // Copy constructor of the AlterationNotifier. 274 // It creates only an empty notifier because the copiable 275 // notifier's observers have to be registered still into that notifier. 283 276 AlterationNotifier(const AlterationNotifier& _notifier) 284 277 : container(_notifier.container) {} 285 278 286 /// \brief Destructor. 287 /// 288 /// Destructor of the AlterationNotifier. 289 /// 279 // \brief Destructor. 280 // 281 // Destructor of the AlterationNotifier. 290 282 ~AlterationNotifier() { 291 283 typename Observers::iterator it; … … 295 287 } 296 288 297 // /\brief Sets the container.298 // /299 // /Sets the container.289 // \brief Sets the container. 290 // 291 // Sets the container. 300 292 void setContainer(const Container& _container) { 301 293 container = &_container; … … 308 300 public: 309 301 310 311 312 /// \brief First item in the container. 313 /// 314 /// Returns the first item in the container. It is 315 /// for start the iteration on the container. 302 // \brief First item in the container. 303 // 304 // Returns the first item in the container. It is 305 // for start the iteration on the container. 316 306 void first(Item& item) const { 317 307 container->first(item); 318 308 } 319 309 320 // /\brief Next item in the container.321 // /322 // /Returns the next item in the container. It is323 // /for iterate on the container.310 // \brief Next item in the container. 311 // 312 // Returns the next item in the container. It is 313 // for iterate on the container. 324 314 void next(Item& item) const { 325 315 container->next(item); 326 316 } 327 317 328 // /\brief Returns the id of the item.329 // /330 // /Returns the id of the item provided by the container.318 // \brief Returns the id of the item. 319 // 320 // Returns the id of the item provided by the container. 331 321 int id(const Item& item) const { 332 322 return container->id(item); 333 323 } 334 324 335 // /\brief Returns the maximum id of the container.336 // /337 // /Returns the maximum id of the container.325 // \brief Returns the maximum id of the container. 326 // 327 // Returns the maximum id of the container. 338 328 int maxId() const { 339 329 return container->maxId(Item()); … … 355 345 public: 356 346 357 /// \brief Notifies all the registed observers about an item added to 358 /// the container. 359 /// 360 /// It notifies all the registed observers about an item added to 361 /// the container. 362 /// 347 // \brief Notifies all the registed observers about an item added to 348 // the container. 349 // 350 // It notifies all the registed observers about an item added to 351 // the container. 363 352 void add(const Item& item) { 364 353 typename Observers::reverse_iterator it; … … 376 365 } 377 366 378 /// \brief Notifies all the registed observers about more item added to 379 /// the container. 380 /// 381 /// It notifies all the registed observers about more item added to 382 /// the container. 383 /// 367 // \brief Notifies all the registed observers about more item added to 368 // the container. 369 // 370 // It notifies all the registed observers about more item added to 371 // the container. 384 372 void add(const std::vector<Item>& items) { 385 373 typename Observers::reverse_iterator it; … … 397 385 } 398 386 399 /// \brief Notifies all the registed observers about an item erased from 400 /// the container. 401 /// 402 /// It notifies all the registed observers about an item erased from 403 /// the container. 404 /// 387 // \brief Notifies all the registed observers about an item erased from 388 // the container. 389 // 390 // It notifies all the registed observers about an item erased from 391 // the container. 405 392 void erase(const Item& item) throw() { 406 393 typename Observers::iterator it = _observers.begin(); … … 417 404 } 418 405 419 /// \brief Notifies all the registed observers about more item erased 420 /// from the container. 421 /// 422 /// It notifies all the registed observers about more item erased from 423 /// the container. 424 /// 406 // \brief Notifies all the registed observers about more item erased 407 // from the container. 408 // 409 // It notifies all the registed observers about more item erased from 410 // the container. 425 411 void erase(const std::vector<Item>& items) { 426 412 typename Observers::iterator it = _observers.begin(); … … 437 423 } 438 424 439 // /\brief Notifies all the registed observers about the container is440 // /built.441 // /442 // /Notifies all the registed observers about the container is built443 // /from an empty container.425 // \brief Notifies all the registed observers about the container is 426 // built. 427 // 428 // Notifies all the registed observers about the container is built 429 // from an empty container. 444 430 void build() { 445 431 typename Observers::reverse_iterator it; … … 457 443 } 458 444 459 // /\brief Notifies all the registed observers about all items are460 // /erased.461 // /462 // /Notifies all the registed observers about all items are erased463 // /from the container.445 // \brief Notifies all the registed observers about all items are 446 // erased. 447 // 448 // Notifies all the registed observers about all items are erased 449 // from the container. 464 450 void clear() { 465 451 typename Observers::iterator it = _observers.begin();
Note: See TracChangeset
for help on using the changeset viewer.