00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012 #ifndef __deal2__smartpointer_h
00013 #define __deal2__smartpointer_h
00014
00015
00016 #include <deal.II/base/config.h>
00017 #include <deal.II/base/subscriptor.h>
00018
00019 DEAL_II_NAMESPACE_OPEN
00020
00058 template<typename T, typename P = void>
00059 class SmartPointer
00060 {
00061 public:
00068 SmartPointer ();
00069
00070
00071
00072
00073
00074
00075
00076
00077 template <class Q>
00078 SmartPointer (const SmartPointer<T,Q> &tt);
00079
00080
00081
00082
00083
00084
00085
00086
00087 SmartPointer (const SmartPointer<T,P> &tt);
00088
00105 SmartPointer (T *t, const char* id);
00106
00119 SmartPointer (T *t);
00120
00121
00126 ~SmartPointer();
00127
00138 SmartPointer<T,P> & operator= (T *tt);
00139
00147 template <class Q>
00148 SmartPointer<T,P> & operator= (const SmartPointer<T,Q> &tt);
00149
00157 SmartPointer<T,P> & operator= (const SmartPointer<T,P> &tt);
00158
00163 void clear ();
00164
00168 operator T* () const;
00169
00176 T& operator * () const;
00177
00184 T * operator -> () const;
00185
00203 template <class Q>
00204 void swap (SmartPointer<T,Q> &tt);
00205
00221 void swap (T *&tt);
00222
00232 std::size_t memory_consumption () const;
00233
00234 private:
00243 T * t;
00248 const char* const id;
00249 };
00250
00251
00252
00253
00254
00255 template <typename T, typename P>
00256 inline
00257 SmartPointer<T,P>::SmartPointer ()
00258 :
00259 t (0), id(typeid(P).name())
00260 {}
00261
00262
00263
00264 template <typename T, typename P>
00265 inline
00266 SmartPointer<T,P>::SmartPointer (T *t)
00267 :
00268 t (t), id(typeid(P).name())
00269 {
00270 if (t != 0)
00271 t->subscribe(id);
00272 }
00273
00274
00275
00276 template <typename T, typename P>
00277 inline
00278 SmartPointer<T,P>::SmartPointer (T *t, const char* id)
00279 :
00280 t (t), id(id)
00281 {
00282 if (t != 0)
00283 t->subscribe(id);
00284 }
00285
00286
00287
00288 template <typename T, typename P>
00289 template <class Q>
00290 inline
00291 SmartPointer<T,P>::SmartPointer (const SmartPointer<T,Q> &tt)
00292 :
00293 t (tt.t), id(tt.id)
00294 {
00295 if (t != 0)
00296 t->subscribe(id);
00297 }
00298
00299
00300
00301 template <typename T, typename P>
00302 inline
00303 SmartPointer<T,P>::SmartPointer (const SmartPointer<T,P> &tt)
00304 :
00305 t (tt.t), id(tt.id)
00306 {
00307 if (t != 0)
00308 t->subscribe(id);
00309 }
00310
00311
00312
00313 template <typename T, typename P>
00314 inline
00315 SmartPointer<T,P>::~SmartPointer ()
00316 {
00317 if (t != 0)
00318 t->unsubscribe(id);
00319 }
00320
00321
00322
00323 template <typename T, typename P>
00324 inline
00325 void
00326 SmartPointer<T,P>::clear ()
00327 {
00328 if (t != 0)
00329 {
00330 t->unsubscribe(id);
00331 delete t;
00332 t = 0;
00333 }
00334 }
00335
00336
00337
00338 template <typename T, typename P>
00339 inline
00340 SmartPointer<T,P> & SmartPointer<T,P>::operator = (T *tt)
00341 {
00342
00343
00344 if (t == tt)
00345 return *this;
00346
00347 if (t != 0)
00348 t->unsubscribe(id);
00349 t = tt;
00350 if (tt != 0)
00351 tt->subscribe(id);
00352 return *this;
00353 }
00354
00355
00356
00357 template <typename T, typename P>
00358 template <class Q>
00359 inline
00360 SmartPointer<T,P> &
00361 SmartPointer<T,P>::operator = (const SmartPointer<T,Q>& tt)
00362 {
00363
00364
00365
00366 if (&tt == this)
00367 return *this;
00368
00369 if (t != 0)
00370 t->unsubscribe(id);
00371 t = static_cast<T*>(tt);
00372 if (tt != 0)
00373 tt->subscribe(id);
00374 return *this;
00375 }
00376
00377
00378
00379 template <typename T, typename P>
00380 inline
00381 SmartPointer<T,P> &
00382 SmartPointer<T,P>::operator = (const SmartPointer<T,P>& tt)
00383 {
00384
00385
00386
00387 if (&tt == this)
00388 return *this;
00389
00390 if (t != 0)
00391 t->unsubscribe(id);
00392 t = static_cast<T*>(tt);
00393 if (tt != 0)
00394 tt->subscribe(id);
00395 return *this;
00396 }
00397
00398
00399
00400 template <typename T, typename P>
00401 inline
00402 SmartPointer<T,P>::operator T* () const
00403 {
00404 return t;
00405 }
00406
00407
00408
00409 template <typename T, typename P>
00410 inline
00411 T & SmartPointer<T,P>::operator * () const
00412 {
00413 Assert(t != 0, ExcNotInitialized());
00414 return *t;
00415 }
00416
00417
00418
00419 template <typename T, typename P>
00420 inline
00421 T * SmartPointer<T,P>::operator -> () const
00422 {
00423 Assert(t != 0, ExcNotInitialized());
00424 return t;
00425 }
00426
00427
00428
00429 template <typename T, typename P>
00430 template <class Q>
00431 inline
00432 void SmartPointer<T,P>::swap (SmartPointer<T,Q> &tt)
00433 {
00434 #ifdef DEBUG
00435 SmartPointer<T,P> aux(t,id);
00436 *this = tt;
00437 tt = aux;
00438 #else
00439 std::swap (t, tt.t);
00440 #endif
00441 }
00442
00443
00444
00445 template <typename T, typename P>
00446 inline
00447 void SmartPointer<T,P>::swap (T *&tt)
00448 {
00449 if (t != 0)
00450 t->unsubscribe (id);
00451
00452 std::swap (t, tt);
00453
00454 if (t != 0)
00455 t->subscribe (id);
00456 }
00457
00458
00459
00460 template <typename T, typename P>
00461 inline
00462 std::size_t
00463 SmartPointer<T,P>::memory_consumption () const
00464 {
00465 return sizeof(SmartPointer<T,P>);
00466 }
00467
00468
00469
00470
00476 template <typename T, typename P, class Q>
00477 inline
00478 void swap (SmartPointer<T,P> &t1, SmartPointer<T,Q> &t2)
00479 {
00480 t1.swap (t2);
00481 }
00482
00483
00484
00492 template <typename T, typename P>
00493 inline
00494 void swap (SmartPointer<T,P> &t1, T *&t2)
00495 {
00496 t1.swap (t2);
00497 }
00498
00499
00500
00508 template <typename T, typename P>
00509 inline
00510 void swap (T *&t1, SmartPointer<T,P> &t2)
00511 {
00512 t2.swap (t1);
00513 }
00514
00515 DEAL_II_NAMESPACE_CLOSE
00516
00517 #endif
00518