00001 /* 00002 * Copyright 2006-2008 The FLWOR Foundation. 00003 * 00004 * Licensed under the Apache License, Version 2.0 (the "License"); 00005 * you may not use this file except in compliance with the License. 00006 * You may obtain a copy of the License at 00007 * 00008 * http://www.apache.org/licenses/LICENSE-2.0 00009 * 00010 * Unless required by applicable law or agreed to in writing, software 00011 * distributed under the License is distributed on an "AS IS" BASIS, 00012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00013 * See the License for the specific language governing permissions and 00014 * limitations under the License. 00015 */ 00016 00017 #ifndef ZORBA_SMARTPTR_API_H 00018 #define ZORBA_SMARTPTR_API_H 00019 00020 #include <zorba/config.h> 00021 00022 namespace zorba { 00023 00024 class ZORBA_DLL_PUBLIC SmartObject 00025 { 00026 protected: 00027 mutable unsigned int theRefCount; 00028 00029 public: 00030 SmartObject() : theRefCount(0) { } 00031 00032 SmartObject(const SmartObject&) : theRefCount(0) { } 00033 00034 virtual ~SmartObject(); 00035 00036 virtual void free(); 00037 00038 long getRefCount() const { return theRefCount; } 00039 00040 void addReference() const { ++theRefCount; } 00041 00042 void removeReference () { 00043 if (--theRefCount == 0) 00044 free(); 00045 } 00046 00047 SmartObject& operator=(const SmartObject&) { return *this; } 00048 }; /* class SmartObject */ 00049 00050 template<class T> 00051 class SmartPtr 00052 { 00053 protected: 00054 T *p; 00055 00056 void init() { 00057 if (p != 0) p->addReference(); 00058 } 00059 00060 template <class otherT> SmartPtr& 00061 assign (const SmartPtr<otherT>& rhs) { 00062 if (p != rhs.get()) 00063 { 00064 if (p) p->removeReference(); 00065 p = static_cast<T*>(rhs.get()); 00066 init(); 00067 } 00068 return *this; 00069 } 00070 00071 public: 00072 SmartPtr(T* realPtr = 0) : p(realPtr) { 00073 init(); 00074 } 00075 00076 SmartPtr(SmartPtr const& rhs) : p(rhs.get()) { 00077 init(); 00078 } 00079 00080 ~SmartPtr() { 00081 if (p) 00082 p->removeReference(); 00083 p = 0; 00084 } 00085 00086 bool isNull () const { return p == 0; } 00087 00088 T* get() const { return p; } 00089 00090 operator T* () { return get(); } 00091 operator const T * () const { return get(); } 00092 00093 T* operator->() const { return p; } 00094 T& operator*() const { return *p; } 00095 00096 bool operator==(SmartPtr const& h) const { return p == h.p; } 00097 bool operator!=(SmartPtr const& h) const { return p != h.p; } 00098 bool operator==(T const* pp) const { return p == pp; } 00099 bool operator!=(T const* pp) const { return p != pp; } 00100 bool operator<(const SmartPtr& h) const { return p < h.p; } 00101 00102 SmartPtr& operator=(SmartPtr const& rhs) { 00103 return assign (rhs); 00104 } 00105 00106 template <class otherT> SmartPtr& operator=(SmartPtr<otherT> const& rhs) { 00107 return assign (rhs); 00108 } 00109 00110 }; // SmartPtr 00111 00112 } // namespace zorba 00113 #endif /* ZORBA_SMARTPTR_API_H */ 00114 /* vim:set et sw=2 ts=2: */