16 #ifndef INCLUDE_NN_NLIB_UNIQUEPTR_H_ 17 #define INCLUDE_NN_NLIB_UNIQUEPTR_H_ 23 #include "nn/nlib/Swap.h" 24 #include "nn/nlib/Hash.h" 27 #if defined(NLIB_CXX11_UNIQUEPTR) && defined(NLIB_CXX11_TEMPLATE_ALIAS) 30 template <
class T,
class DEL = std::default_delete<T> >
31 using UniquePtr = std::unique_ptr<T, DEL>;
33 using DefaultDelete = std::default_delete<T>;
42 struct DefaultDelete {
50 struct DefaultDelete<T[]> {
57 NLIB_STATIC_ASSERT(IsEmpty<DefaultDelete<int> >::value&& IsEmpty<DefaultDelete<
int[]> >::value);
61 template <
class T,
class DEL,
bool DEL_EMPTY>
64 UniquePtrBase() : ptr_(NULL), deleter_() {}
65 explicit UniquePtrBase(T* ptr) : ptr_(ptr), deleter_() {}
66 UniquePtrBase(T* ptr,
const DEL& del) : ptr_(ptr), deleter_(del) {}
69 DEL& get_deleter() {
return deleter_; }
70 const DEL& get_deleter()
const {
return deleter_; }
75 swap(this->ptr_, rhs.ptr_);
76 swap(this->deleter_, rhs.deleter_);
81 template <
class T,
class DEL>
82 class UniquePtrBase<T, DEL, true> :
public DEL {
84 UniquePtrBase() : ptr_(NULL) {}
85 explicit UniquePtrBase(T* ptr) : ptr_(ptr) {}
86 UniquePtrBase(T* ptr,
const DEL& del) : DEL(del), ptr_(ptr) {}
89 DEL& get_deleter() {
return *
this; }
90 const DEL& get_deleter()
const {
return *
this; }
94 swap(this->ptr_, rhs.ptr_);
100 struct IsCompleteType
101 :
public IntegralConstant<bool, (sizeof(S) != 0 || sizeof(S) == 0)> {};
104 struct IsCompleteType<void> :
public TrueType {};
108 template <
class T,
class DEL = DefaultDelete<T> >
110 typedef detail::UniquePtrBase<T, DEL, IsEmpty<DEL>::value> BaseType;
121 NLIB_MOVE_MEMBER_HELPER_1(
UniquePtr, BaseType)
126 if (this->ptr_) get_deleter()(this->ptr_);
131 if (p != this->ptr_) {
134 if (old) get_deleter()(old);
138 NLIB_ASSERT(this->ptr_ != NULL);
142 NLIB_ASSERT(this->ptr_ != NULL);
158 size_t GetHash()
const {
return Hash<T*>()(this->
get()); }
160 const DEL&
get_deleter()
const {
return BaseType::get_deleter(); }
165 template <
class S,
class D>
167 template <
class S,
class D>
172 template <
class T,
class DEL>
173 class UniquePtr<T[], DEL> :
public detail::UniquePtrBase<T, DEL, IsEmpty<DEL>::value> {
174 typedef detail::UniquePtrBase<T, DEL, IsEmpty<DEL>::value> BaseType;
184 UniquePtr(T* p,
const DEL& del) : BaseType(p, del) {}
185 NLIB_MOVE_MEMBER_HELPER_1(
UniquePtr, BaseType)
188 get_deleter()(this->ptr_);
193 if (p != this->ptr_) {
196 if (old) get_deleter()(old);
200 NLIB_ASSERT(this->ptr_ != NULL);
204 NLIB_ASSERT(this->ptr_ != NULL);
216 T& operator[](
size_t n) {
return get()[n]; }
217 const T& operator[](
size_t n)
const {
return get()[n]; }
218 size_t GetHash()
const {
return Hash<T*>()(this->
get()); }
219 DEL& get_deleter() {
return BaseType::get_deleter(); }
220 const DEL& get_deleter()
const {
return BaseType::get_deleter(); }
225 template <
class S,
class D>
227 template <
class S,
class D>
232 template <
class T1,
class D1,
class T2,
class D2>
234 return rhs.get() == lhs.get();
237 template <
class T1,
class D1>
242 template <
class T1,
class D1>
247 template <
class T1,
class D1,
class T2,
class D2>
249 return rhs.get() != lhs.get();
252 template <
class T1,
class D1>
254 return static_cast<bool>(lhs);
257 template <
class T1,
class D1>
259 return static_cast<bool>(rhs);
264 #ifndef NLIB_STD_SWAP_WORKAROUND 267 NLIB_DEFINE_STD_SWAP_T_BEGIN1(
std)
270 NLIB_DEFINE_STD_SWAP_T2(T, DEL, NLIB_NS::UniquePtr)
272 #ifndef NLIB_STD_SWAP_WORKAROUND 275 NLIB_DEFINE_STD_SWAP_T_END1(
std)
278 #ifndef NLIB_CXX11_TEMPLATE_ALIAS 281 NLIB_DEFINE_STD_HASH_T_BEGIN1(
std)
284 NLIB_DEFINE_STD_HASH_T2(T, DEL, NLIB_NS::UniquePtr)
286 #ifndef NLIB_CXX11_TEMPLATE_ALIAS 289 NLIB_DEFINE_STD_HASH_T_END1(
std)
309 template <
class T,
class ALLOC,
bool DEL_EMPTY>
310 class DefaultDeleteExBase {
312 DefaultDeleteExBase() : al() {}
313 explicit DefaultDeleteExBase(
const ALLOC& al_) : al(al_) {}
316 ALLOC& get_allocator() {
return al; }
323 template <
class T,
class ALLOC>
324 class DefaultDeleteExBase<T, ALLOC, true> :
public ALLOC {
326 DefaultDeleteExBase() {}
327 explicit DefaultDeleteExBase(
const ALLOC& al_) { NLIB_UNUSED(al_); }
330 ALLOC& get_allocator() {
return *
this; }
335 template <
class T,
class ALLOC = std::allocator<T> >
336 struct DefaultDeleteEx :
public detail::DefaultDeleteExBase<T, ALLOC, IsEmpty<ALLOC>::value> {
340 typedef detail::DefaultDeleteExBase<T, ALLOC, IsEmpty<ALLOC>::value> BaseType;
342 ALLOC& al = BaseType::get_allocator();
349 template <
class T,
class ALLOC>
350 struct DefaultDeleteEx<T[], ALLOC>
351 :
public detail::DefaultDeleteExBase<T, ALLOC, IsEmpty<ALLOC>::value> {
359 typedef detail::DefaultDeleteExBase<T, ALLOC, IsEmpty<ALLOC>::value> BaseType;
363 ALLOC& al = BaseType::get_allocator();
372 #ifdef NLIB_CXX11_DEFAULTED_AND_DELETED_FUNCTIONS 373 template<
class T,
class DEL>
376 template<
class T,
class DEL>
380 #endif // INCLUDE_NN_NLIB_UNIQUEPTR_H_ ~UniquePtr() noexcept
デストラクタです。ポインタがNULLでなければデリータを実行して削除します。
UniquePtr(T *p) noexcept
ポインタを設定します。
C++11の標準ヘッダとなるtype_traitsの代用定義です。 コンパイラや標準ライブラリによってサポートされてい...
DEL & get_deleter()
デリータを取得します。
constexpr UniquePtr(nullptr_t) noexcept
引数にnullptrを与えた場合に呼び出されます。
#define NLIB_DISALLOW_COPY_AND_ASSIGN(TypeName)
TypeName で指定されたクラスのコピーコンストラクタと代入演算子を禁止します。
#define NLIB_SAFE_BOOL(class_name, exp)
クラス内に安全なoperator bool()を定義します。 可能であればC++11のexplicit boolを利用します。 ...
T element_type
Tがtypedefされています。
UniquePtrはポインタの所有権を保持し、UniquePtrがスコープから出るときにデストラクタでポインタをDELで指...
bool operator==(const HeapHash &rhs, const HeapHash &lhs)
2つのサマリを比較して等価ならば、trueを返します。
bool operator!=(const HeapHash &rhs, const HeapHash &lhs)
2つのサマリを比較して等価でなければ、trueを返します。
void reset(T *p=0) noexcept
ポインタを置き換えます。置き換えられたポインタは削除されます。
constexpr UniquePtr() noexcept
デフォルトコンストラクタです。
size_t GetHash() const
ポインタに対してハッシュ値の計算を行い、計算結果を返します。
UniquePtr & operator=(nullptr_t) noexcept
nullptrを代入します。
AddRef< T >::type operator*() const
ポインタの参照外しを行います。
void swap(UniquePtr &rhs) noexcept
格納されているポインタをスワップします。
T * operator->() const noexcept
ポインタを返します。
DEL deleter_type
DELがtypedefされています。
const DEL & get_deleter() const
デリータを取得します。
#define NLIB_NOEXCEPT
環境に合わせてnoexcept 又は同等の定義がされます。
#define NLIB_CEXPR
利用可能であればconstexprが定義されます。そうでない場合は空文字列です。
TimeSpan operator*(int i, const TimeSpan &rhs) noexcept
rhs を i 倍します。
UniquePtr(T *p, const DEL &del)
ポインタとデリータを設定します。
#define NLIB_FINAL
利用可能であればfinalが定義されます。そうでない場合は空文字列です。
#define NLIB_STATIC_ASSERT(exp)
静的アサートが定義されます。利用可能であればstatic_assertを利用します。
T * pointer_type
T*がtypedefされています。
T * release() noexcept
ポインタの所有権を手放し、ポインタを返します。