00001 // This file may be redistributed and modified only under the terms of 00002 // the GNU Lesser General Public License (See COPYING for details). 00003 // Copyright (C) 2000 Aloril 00004 // Copyright (C) 2000-2005 Al Riddoch 00005 00006 #ifndef ATLAS_OBJECTS_SMARTPTR_H 00007 #define ATLAS_OBJECTS_SMARTPTR_H 00008 00009 #include <Atlas/Exception.h> 00010 00011 namespace Atlas { namespace Objects { 00012 00013 class NullSmartPtrDereference : public Atlas::Exception 00014 { 00015 public: 00016 NullSmartPtrDereference() : Atlas::Exception("Null SmartPtr dereferenced") {} 00017 virtual ~NullSmartPtrDereference() throw (); 00018 }; 00019 00020 template <class T> 00021 class SmartPtr 00022 { 00023 public: 00024 typedef T DataT; 00025 00026 typedef typename T::iterator iterator; 00027 typedef typename T::const_iterator const_iterator; 00028 00029 SmartPtr() : ptr(T::alloc()) { 00030 } 00031 SmartPtr(const SmartPtr<T>& a) : ptr(a.get()) { 00032 incRef(); 00033 } 00034 SmartPtr(T *a_ptr) : ptr(a_ptr) 00035 { 00036 incRef(); 00037 } 00038 template<class oldType> 00039 explicit SmartPtr(const SmartPtr<oldType>& a) : ptr(a.get()) { 00040 } 00041 ~SmartPtr() { 00042 decRef(); 00043 } 00044 SmartPtr& operator=(const SmartPtr<T>& a) { 00045 if (a.get() != this->get()) { 00046 decRef(); 00047 ptr = a.get(); 00048 incRef(); 00049 } 00050 return *this; 00051 } 00052 template<class newType> 00053 operator SmartPtr<newType>() const { 00054 return SmartPtr<newType>(ptr); 00055 } 00056 template<class newType> 00057 operator SmartPtr<const newType>() const { 00058 return SmartPtr<const newType>(ptr); 00059 } 00060 bool isValid() const { 00061 return ptr != 0; 00062 } 00063 T& operator*() const { 00064 if (ptr == 0) { 00065 throw NullSmartPtrDereference(); 00066 } 00067 return *ptr; 00068 } 00069 T* operator->() const { 00070 if (ptr == 0) { 00071 throw NullSmartPtrDereference(); 00072 } 00073 return ptr; 00074 } 00075 T* get() const { 00076 return ptr; 00077 } 00078 SmartPtr<T> copy() const 00079 { 00080 SmartPtr<T> ret = SmartPtr(ptr->copy()); 00081 ret.decRef(); 00082 return ret; 00083 } 00084 SmartPtr<T> getDefaultObject() const 00085 { 00086 return SmartPtr(ptr->getDefaultObject()); 00087 } 00088 // If you want to make these protected, please ensure that the 00089 // detructor is made virtual to ensure your new class bahaves 00090 // correctly. 00091 private: 00092 void decRef() const { 00093 if (ptr != 0) { 00094 ptr->decRef(); 00095 } 00096 } 00097 void incRef() const { 00098 if (ptr != 0) { 00099 ptr->incRef(); 00100 } 00101 } 00102 T * ptr; 00103 }; 00104 00105 template<typename returnPtrType, class fromType> 00106 returnPtrType smart_dynamic_cast(const SmartPtr<fromType> & o) 00107 { 00108 return returnPtrType(dynamic_cast<typename returnPtrType::DataT*>(o.get())); 00109 } 00110 00111 template<typename returnPtrType, class fromType> 00112 returnPtrType smart_static_cast(const SmartPtr<fromType> & o) 00113 { 00114 return returnPtrType((typename returnPtrType::DataT *)o.get()); 00115 } 00116 00117 } } // namespace Atlas::Objects 00118 00119 #endif // ATLAS_OBJECTS_SMARTPTR_H
Copyright 2000-2004 the respective authors.
This document can be licensed under the terms of the GNU Free Documentation License or the GNU General Public License and may be freely distributed under the terms given by one of these licenses.