201 ObserverBase& operator=(const ObserverBase& copy); |
201 ObserverBase& operator=(const ObserverBase& copy); |
202 |
202 |
203 protected: |
203 protected: |
204 |
204 |
205 Notifier* notifier; |
205 Notifier* notifier; |
206 int notifier_index; |
206 typename std::list<ObserverBase*>::iterator index; |
207 |
207 |
208 /// \brief The member function to notificate the observer about an |
208 /// \brief The member function to notificate the observer about an |
209 /// item is added to the container. |
209 /// item is added to the container. |
210 /// |
210 /// |
211 /// The add() member function notificates the observer about an item |
211 /// The add() member function notificates the observer about an item |
212 /// is added to the container. It have to be overrided in the |
212 /// is added to the container. It have to be overrided in the |
213 /// subclasses. |
213 /// subclasses. |
214 |
|
215 virtual void add(const Item&) = 0; |
214 virtual void add(const Item&) = 0; |
216 |
215 |
217 /// \brief The member function to notificate the observer about |
216 /// \brief The member function to notificate the observer about |
218 /// more item is added to the container. |
217 /// more item is added to the container. |
219 /// |
218 /// |
220 /// The add() member function notificates the observer about more item |
219 /// The add() member function notificates the observer about more item |
221 /// is added to the container. It have to be overrided in the |
220 /// is added to the container. It have to be overrided in the |
222 /// subclasses. |
221 /// subclasses. |
223 |
222 virtual void add(const std::vector<Item>& items) = 0; |
224 virtual void add(const std::vector<Item>& items) { |
|
225 int i; |
|
226 try { |
|
227 for (i = 0; i < (int)items.size(); ++i) { |
|
228 add(items[i]); |
|
229 } |
|
230 } catch (...) { |
|
231 for (int j = 0; j < i; ++j) { |
|
232 add(items[j]); |
|
233 } |
|
234 throw; |
|
235 } |
|
236 } |
|
237 |
223 |
238 /// \brief The member function to notificate the observer about an |
224 /// \brief The member function to notificate the observer about an |
239 /// item is erased from the container. |
225 /// item is erased from the container. |
240 /// |
226 /// |
241 /// The erase() member function notificates the observer about an |
227 /// The erase() member function notificates the observer about an |
242 /// item is erased from the container. It have to be overrided in |
228 /// item is erased from the container. It have to be overrided in |
243 /// the subclasses. |
229 /// the subclasses. |
244 |
|
245 virtual void erase(const Item&) = 0; |
230 virtual void erase(const Item&) = 0; |
246 |
231 |
247 /// \brief The member function to notificate the observer about |
232 /// \brief The member function to notificate the observer about |
248 /// more item is erased from the container. |
233 /// more item is erased from the container. |
249 /// |
234 /// |
250 /// The erase() member function notificates the observer about more item |
235 /// The erase() member function notificates the observer about more item |
251 /// is erased from the container. It have to be overrided in the |
236 /// is erased from the container. It have to be overrided in the |
252 /// subclasses. |
237 /// subclasses. |
253 virtual void erase(const std::vector<Item>& items) { |
238 virtual void erase(const std::vector<Item>& items) = 0; |
254 for (int i = 0; i < (int)items.size(); ++i) { |
|
255 erase(items[i]); |
|
256 } |
|
257 } |
|
258 |
239 |
259 /// \brief The member function to notificate the observer about the |
240 /// \brief The member function to notificate the observer about the |
260 /// container is built. |
241 /// container is built. |
261 /// |
242 /// |
262 /// The build() member function notificates the observer about the |
243 /// The build() member function notificates the observer about the |
263 /// container is built from an empty container. It have to be |
244 /// container is built from an empty container. It have to be |
264 /// overrided in the subclasses. |
245 /// overrided in the subclasses. |
265 |
246 |
266 virtual void build() { |
247 virtual void build() = 0; |
267 Item it; |
|
268 try { |
|
269 for (notifier->first(it); it != INVALID; notifier->next(it)) { |
|
270 add(it); |
|
271 } |
|
272 } catch (...) { |
|
273 Item jt; |
|
274 for (notifier->first(jt); jt != it; notifier->next(jt)) { |
|
275 erase(jt); |
|
276 } |
|
277 throw; |
|
278 } |
|
279 } |
|
280 |
248 |
281 /// \brief The member function to notificate the observer about all |
249 /// \brief The member function to notificate the observer about all |
282 /// items are erased from the container. |
250 /// items are erased from the container. |
283 /// |
251 /// |
284 /// The clear() member function notificates the observer about all |
252 /// The clear() member function notificates the observer about all |
285 /// items are erased from the container. It have to be overrided in |
253 /// items are erased from the container. It have to be overrided in |
286 /// the subclasses. |
254 /// the subclasses. |
287 virtual void clear() { |
255 virtual void clear() = 0; |
288 Item it; |
|
289 for (notifier->first(it); it != INVALID; notifier->next(it)) { |
|
290 erase(it); |
|
291 } |
|
292 } |
|
293 |
256 |
294 }; |
257 }; |
295 |
258 |
296 protected: |
259 protected: |
297 |
260 |
298 const Container* container; |
261 const Container* container; |
299 |
262 |
300 typedef std::vector<ObserverBase*> Observers; |
263 typedef std::list<ObserverBase*> Observers; |
301 Observers observers; |
264 Observers observers; |
302 |
265 |
303 |
266 |
304 public: |
267 public: |
305 |
268 |
462 /// |
425 /// |
463 /// It notifies all the registed observers about more item erased from |
426 /// It notifies all the registed observers about more item erased from |
464 /// the container. |
427 /// the container. |
465 /// |
428 /// |
466 void erase(const std::vector<Item>& items) { |
429 void erase(const std::vector<Item>& items) { |
467 int i = 0; |
430 typename Observers::iterator it = observers.begin(); |
468 while (i != (int)observers.size()) { |
431 while (it != observers.end()) { |
469 try { |
432 try { |
470 observers[i]->erase(items); |
433 (*it)->erase(items); |
471 ++i; |
434 ++it; |
472 } catch (const ImmediateDetach&) { |
435 } catch (const ImmediateDetach&) { |
473 observers[i]->detach(); |
436 it = observers.erase(it); |
|
437 (*it)->index = observers.end(); |
|
438 (*it)->notifier = 0; |
474 } |
439 } |
475 } |
440 } |
476 } |
441 } |
477 |
442 |
478 /// \brief Notifies all the registed observers about the container is |
443 /// \brief Notifies all the registed observers about the container is |
479 /// built. |
444 /// built. |
480 /// |
445 /// |
481 /// Notifies all the registed observers about the container is built |
446 /// Notifies all the registed observers about the container is built |
482 /// from an empty container. |
447 /// from an empty container. |
483 void build() { |
448 void build() { |
484 typename Observers::iterator it; |
449 typename Observers::reverse_iterator it; |
485 try { |
450 try { |
486 for (it = observers.begin(); it != observers.end(); ++it) { |
451 for (it = observers.rbegin(); it != observers.rend(); ++it) { |
487 (*it)->build(); |
452 (*it)->build(); |
488 } |
453 } |
489 } catch (...) { |
454 } catch (...) { |
490 typename Observers::iterator jt; |
455 typename Observers::iterator jt; |
491 for (jt = observers.begin(); jt != it; ++jt) { |
456 for (jt = it.base(); jt != observers.end(); ++jt) { |
492 (*it)->clear(); |
457 (*jt)->clear(); |
493 } |
458 } |
494 throw; |
459 throw; |
495 } |
460 } |
496 } |
461 } |
497 |
462 |