3 #ifndef INCLUDE_NN_NLIB_UNIQUEPTR_H_
4 #define INCLUDE_NN_NLIB_UNIQUEPTR_H_
10 #include "nn/nlib/Swap.h"
11 #include "nn/nlib/Hash.h"
14 #if defined(NLIB_CXX11_UNIQUEPTR) && defined(NLIB_CXX11_TEMPLATE_ALIAS)
17 template <
class T,
class DEL = std::default_delete<T> >
18 using UniquePtr = std::unique_ptr<T, DEL>;
20 using DefaultDelete = std::default_delete<T>;
29 struct DefaultDelete {
37 struct DefaultDelete<T[]> {
44 NLIB_STATIC_ASSERT(IsEmpty<DefaultDelete<int> >::value&& IsEmpty<DefaultDelete<
int[]> >::value);
48 template <
class T,
class DEL,
bool DEL_EMPTY>
51 UniquePtrBase() : m_Ptr(NULL), m_Deleter() {}
52 explicit UniquePtrBase(T* ptr) : m_Ptr(ptr), m_Deleter() {}
53 UniquePtrBase(T* ptr,
const DEL& del) : m_Ptr(ptr), m_Deleter(del) {}
56 DEL& get_deleter() {
return m_Deleter; }
57 const DEL& get_deleter()
const {
return m_Deleter; }
62 swap(this->m_Ptr, rhs.m_Ptr);
63 swap(this->m_Deleter, rhs.m_Deleter);
68 template <
class T,
class DEL>
69 class UniquePtrBase<T, DEL, true> :
public DEL {
71 UniquePtrBase() : m_Ptr(NULL) {}
72 explicit UniquePtrBase(T* ptr) : m_Ptr(ptr) {}
73 UniquePtrBase(T* ptr,
const DEL& del) : DEL(del), m_Ptr(ptr) {}
76 DEL& get_deleter() {
return *
this; }
77 const DEL& get_deleter()
const {
return *
this; }
81 swap(this->m_Ptr, rhs.m_Ptr);
88 :
public IntegralConstant<bool, (sizeof(S) != 0 || sizeof(S) == 0)> {};
91 struct IsCompleteType<void> :
public TrueType {};
95 template <
class T,
class DEL = DefaultDelete<T> >
97 typedef detail::UniquePtrBase<T, DEL, IsEmpty<DEL>::value> BaseType;
108 NLIB_MOVE_MEMBER_HELPER_1(
UniquePtr, BaseType)
113 if (this->m_Ptr) get_deleter()(this->m_Ptr);
118 if (p != this->m_Ptr) {
119 T* old = this->m_Ptr;
121 if (old) get_deleter()(old);
125 NLIB_ASSERT(this->m_Ptr != NULL);
129 NLIB_ASSERT(this->m_Ptr != NULL);
145 size_t GetHash()
const {
return Hash<T*>()(this->
get()); }
147 const DEL&
get_deleter()
const {
return BaseType::get_deleter(); }
152 template <
class S,
class D>
154 template <
class S,
class D>
159 template <
class T,
class DEL>
160 class UniquePtr<T[], DEL> :
public detail::UniquePtrBase<T, DEL, IsEmpty<DEL>::value> {
161 typedef detail::UniquePtrBase<T, DEL, IsEmpty<DEL>::value> BaseType;
164 typedef T* pointer_type;
165 typedef DEL deleter_type;
166 typedef T element_type;
171 UniquePtr(T* p,
const DEL& del) : BaseType(p, del) {}
172 NLIB_MOVE_MEMBER_HELPER_1(UniquePtr, BaseType)
175 get_deleter()(this->m_Ptr);
180 if (p != this->m_Ptr) {
181 T* old = this->m_Ptr;
183 if (old) get_deleter()(old);
187 NLIB_ASSERT(this->m_Ptr != NULL);
191 NLIB_ASSERT(this->m_Ptr != NULL);
203 T& operator[](
size_t n) {
return get()[n]; }
204 const T& operator[](
size_t n)
const {
return get()[n]; }
205 size_t GetHash()
const {
return Hash<T*>()(this->
get()); }
206 DEL& get_deleter() {
return BaseType::get_deleter(); }
207 const DEL& get_deleter()
const {
return BaseType::get_deleter(); }
212 template <
class S,
class D>
213 bool operator==(
const UniquePtr<S, D>& p)
const;
214 template <
class S,
class D>
215 bool operator!=(
const UniquePtr<S, D>& p)
const;
219 template <
class T1,
class D1,
class T2,
class D2>
221 return rhs.get() == lhs.get();
224 template <
class T1,
class D1>
229 template <
class T1,
class D1>
234 template <
class T1,
class D1,
class T2,
class D2>
236 return rhs.get() != lhs.get();
239 template <
class T1,
class D1>
241 return static_cast<bool>(lhs);
244 template <
class T1,
class D1>
246 return static_cast<bool>(rhs);
251 #ifndef NLIB_STD_SWAP_WORKAROUND
254 NLIB_DEFINE_STD_SWAP_T_BEGIN1(
std)
257 NLIB_DEFINE_STD_SWAP_T2(T, DEL, NLIB_NS::UniquePtr)
259 #ifndef NLIB_STD_SWAP_WORKAROUND
262 NLIB_DEFINE_STD_SWAP_T_END1(
std)
265 #ifndef NLIB_CXX11_TEMPLATE_ALIAS
268 NLIB_DEFINE_STD_HASH_T_BEGIN1(
std)
271 NLIB_DEFINE_STD_HASH_T2(T, DEL, NLIB_NS::UniquePtr)
273 #ifndef NLIB_CXX11_TEMPLATE_ALIAS
276 NLIB_DEFINE_STD_HASH_T_END1(
std)
296 template <
class T,
class ALLOC,
bool DEL_EMPTY>
297 class DefaultDeleteExBase {
299 DefaultDeleteExBase() : al() {}
300 explicit DefaultDeleteExBase(
const ALLOC& al_) : al(al_) {}
303 ALLOC& get_allocator() {
return al; }
310 template <
class T,
class ALLOC>
311 class DefaultDeleteExBase<T, ALLOC, true> :
public ALLOC {
313 DefaultDeleteExBase() {}
314 explicit DefaultDeleteExBase(
const ALLOC& al_) { NLIB_UNUSED(al_); }
317 ALLOC& get_allocator() {
return *
this; }
322 template <
class T,
class ALLOC = std::allocator<T> >
323 struct DefaultDeleteEx :
public detail::DefaultDeleteExBase<T, ALLOC, IsEmpty<ALLOC>::value> {
327 typedef detail::DefaultDeleteExBase<T, ALLOC, IsEmpty<ALLOC>::value> BaseType;
329 ALLOC& al = BaseType::get_allocator();
336 template <
class T,
class ALLOC>
337 struct DefaultDeleteEx<T[], ALLOC>
338 :
public detail::DefaultDeleteExBase<T, ALLOC, IsEmpty<ALLOC>::value> {
346 typedef detail::DefaultDeleteExBase<T, ALLOC, IsEmpty<ALLOC>::value> BaseType;
350 ALLOC& al = BaseType::get_allocator();
359 #endif // INCLUDE_NN_NLIB_UNIQUEPTR_H_
#define NLIB_NOEXCEPT
Defines noexcept geared to the environment, or the equivalent.
~UniquePtr() noexcept
Destructor. If the pointer is not NULL, executes the deleter and deletes.
UniquePtr(T *p) noexcept
Sets a pointer.
Substitute definitions for the C++11 standard header type_traits. These substitute definitions are us...
DEL & get_deleter()
Gets the deleter.
T * operator->() const noexcept
Returns the pointer.
constexpr UniquePtr(nullptr_t) noexcept
This function is called if nullptr has been passed to a parameter.
#define NLIB_FINAL
Defines final if it is available for use. If not, holds an empty string.
#define NLIB_DISALLOW_COPY_AND_ASSIGN(TypeName)
Prohibits use of the copy constructor and assignment operator for the class specified by TypeName...
#define NLIB_SAFE_BOOL(class_name, exp)
Defines a safe operator bool function in the class. Uses the C++11 explicit bool if it is available f...
T element_type
Defines T using typedef.
UniquePtr owns the pointer, and when it goes out of scope, the pointer is released by the destructor ...
bool operator==(const HeapHash &rhs, const HeapHash &lhs)
Returns true if the two compared summaries are equal.
bool operator!=(const HeapHash &rhs, const HeapHash &lhs)
Returns true if the two compared summaries are not equal.
void reset(T *p=0) noexcept
Replaces a pointer. The replaced pointer is deleted.
constexpr UniquePtr() noexcept
Instantiates the object with default parameters (default constructor).
UniquePtr & operator=(nullptr_t) noexcept
Substitutes for nullptr.
#define NLIB_CEXPR
Defines constexpr if it is available for use. If not, holds an empty string.
void swap(UniquePtr &rhs) noexcept
Swaps the pointer that is being stored.
size_t GetHash() const
Computes the hash value for the pointer and returns the calculation result.
const DEL & get_deleter() const
Gets the deleter.
DEL deleter_type
Defines DEL using typedef.
A file that contains the configuration information for each development environment.
TimeSpan operator*(int i, const TimeSpan &rhs) noexcept
Increases rhs by a factor of i.
AddRef< T >::type operator*() const
Dereferences the pointer.
UniquePtr(T *p, const DEL &del)
Sets a pointer and a deleter.
#define NLIB_STATIC_ASSERT(exp)
Defines a static assertion. Uses static_assert if it is available for use.
T * pointer_type
Defines T* using typedef.
T * release() noexcept
Release ownership of the pointer and returns the pointer.