39 template <typename _Ty, typename _Decayed = typename std::decay<_Ty>::type,
40 typename std::enable_if<std::is_copy_constructible<_Decayed>::value,
int>::type = 0>
44 Emplace<_Decayed>(std::forward<_Ty>(val));
47 template <
typename _Ty,
typename... _Args>
51 using _Decayed =
typename std::decay<_Ty>::type;
54 EmplaceDecayed<_Decayed>(std::forward<_Args>(args)...);
66 MoveFrome(std::move(rhs));
76 inline const std::type_info&
GetType() const noexcept
78 const std::type_info*
const info = GetTypeinfo();
90 return GetTypeinfo() !=
nullptr;
95 template <
typename _Ty,
typename... _Args>
98 using _Decayed =
typename std::decay<_Ty>::type;
101 EmplaceDecayed<_Decayed>(std::forward<_Args>(args)...);
108 Any old = std::move(rhs);
109 rhs = std::move(*
this);
110 *
this = std::move(old);
122 template <
typename _Ty>
125 return const_cast<_Ty*
>(
const_cast<const Any*
>(
this)->CastPtr<_Ty>());
130 template <
typename _Ty>
133 static_assert(!std::is_void<_Ty>::value,
"oc::Any cannot contain void");
135 const std::type_info*
const info = GetTypeinfo();
136 if (info && (*info ==
typeid(std::decay<_Ty>::type)))
140 return static_cast<const _Ty*
>(GetSmallData());
144 return static_cast<const _Ty*
>(GetBigData());
153 template <
typename _Ty>
156 using _Decayed =
typename std::decay<_Ty>::type;
158 const auto ptr = CastPtr<_Decayed>();
161 throw std::bad_cast();
163 return static_cast<_Ty
>(*ptr);
169 template <
typename _Ty>
172 using _Decayed =
typename std::decay<_Ty>::type;
174 const auto ptr = CastPtr<_Decayed>();
177 throw std::bad_cast();
179 return static_cast<_Ty
>(*ptr);
182 Any& operator=(
const Any& rhs)
188 Any& operator=(Any&& rhs)
noexcept
191 MoveFrome(std::move(rhs));
196 const std::type_info*& GetTypeinfo()
198 return storage_.small_.info_;
201 const std::type_info* GetTypeinfo()
const
203 return storage_.small_.info_;
206 template <
typename _Decayed,
typename... _Args>
207 inline void EmplaceDecayed(_Args&&... args)
209 Store<_Decayed>(IsSmallSize<_Decayed>{}, std::forward<_Args>(args)...);
212 template <
typename _Decayed,
typename... _Args>
213 void Store(std::true_type, _Args&&... args)
215 storage_.is_small_ =
true;
216 GetTypeinfo() = &
typeid(_Decayed);
217 GetSmallRTTI() = SmallStorageRTTI::make<_Decayed>();
219 ::new (GetSmallData()) _Decayed(std::forward<_Args>(args)...);
222 template <typename _Decayed, typename... _Args>
223 void Store(std::false_type, _Args&&... args)
225 storage_.is_small_ =
false;
226 GetTypeinfo() = &
typeid(_Decayed);
227 GetBigRTTI() = BigStorageRTTI::make<_Decayed>();
229 GetBigData() = ::new _Decayed(std::forward<_Args>(args)...);
238 GetSmallRTTI().destroy(GetSmallData());
242 GetBigRTTI().destroy(GetBigData());
243 GetBigData() =
nullptr;
245 GetTypeinfo() =
nullptr;
249 void CopyFrom(
const Any& rhs)
253 GetTypeinfo() = rhs.GetTypeinfo();
254 storage_.is_small_ = rhs.storage_.is_small_;
256 if (rhs.HasSmallType())
258 GetSmallRTTI() = rhs.GetSmallRTTI();
259 GetSmallRTTI().copy(GetSmallData(), rhs.GetSmallData());
263 GetBigRTTI() = rhs.GetBigRTTI();
264 GetBigData() = GetBigRTTI().copy(rhs.GetBigData());
269 void MoveFrome(Any&& rhs)
noexcept
273 GetTypeinfo() = rhs.GetTypeinfo();
274 storage_.is_small_ = rhs.storage_.is_small_;
276 if (rhs.HasSmallType())
278 GetSmallRTTI() = rhs.GetSmallRTTI();
279 GetSmallRTTI().move(GetSmallData(), rhs.GetSmallData());
283 GetBigRTTI() = rhs.GetBigRTTI();
284 GetBigData() = rhs.GetBigData();
285 rhs.GetTypeinfo() =
nullptr;
290 inline void* GetSmallData()
292 return storage_.small_.buffer_;
295 inline const void* GetSmallData()
const
297 return storage_.small_.buffer_;
300 inline void*& GetBigData()
302 return storage_.big_.ptr_;
305 inline void* GetBigData()
const
307 return storage_.big_.ptr_;
310 inline bool HasSmallType()
const
312 return storage_.is_small_;
316 static const auto ANY_SMALL_SPACE_SIZE = 8U;
318 template <
typename _Ty>
319 struct IsSmallSize :
public std::bool_constant<sizeof(_Ty) <= ANY_SMALL_SPACE_SIZE>
323 struct BigStorageRTTI
325 using DestroyFunc = void(void*);
326 using CopyFunc = void*(const void*);
334 template <typename _Ty>
335 static inline BigStorageRTTI make()
338 rtti.destroy = &BigStorageRTTI::Destroy<_Ty>;
339 rtti.copy = &BigStorageRTTI::Copy<_Ty>;
343 template <typename _Ty>
344 static void Destroy(void* const ptr) noexcept
346 ::delete static_cast<_Ty*>(ptr);
349 template <typename _Ty>
350 static void* Copy(const void* const ptr) noexcept
352 return ::new _Ty(*static_cast<const _Ty*>(ptr));
355 DestroyFunc* destroy;
359 struct SmallStorageRTTI
361 using DestroyFunc = void(void*);
362 using CopyFunc = void*(void*, const void*);
363 using MoveFunc = void*(void*, void*);
372 template <typename _Ty>
373 static inline SmallStorageRTTI make()
375 SmallStorageRTTI rtti;
376 rtti.destroy = &SmallStorageRTTI::Destroy<_Ty>;
377 rtti.copy = &SmallStorageRTTI::Copy<_Ty>;
378 rtti.move = &SmallStorageRTTI::Move<_Ty>;
382 template <typename _Ty>
383 static void Destroy(void* const ptr) noexcept
387 _Ty& obj = *(static_cast<_Ty* const>(ptr));
392 template <typename _Ty>
393 static void* Copy(void* const target, const void* const ptr) noexcept
395 return ::new (static_cast<_Ty*>(target)) _Ty(*static_cast<const _Ty*>(ptr));
398 template <typename _Ty>
399 static void* Move(void* const target, void* const ptr) noexcept
401 return ::new (static_cast<_Ty*>(target)) _Ty(std::move(*static_cast<_Ty*>(ptr)));
404 DestroyFunc* destroy;
410 inline SmallStorageRTTI& GetSmallRTTI()
412 return storage_.small_.rtti_;
415 inline const SmallStorageRTTI& GetSmallRTTI() const
417 return storage_.small_.rtti_;
420 inline BigStorageRTTI& GetBigRTTI()
422 return storage_.big_.rtti_;
425 inline const BigStorageRTTI& GetBigRTTI() const
427 return storage_.big_.rtti_;
433 const std::type_info* info_;
434 SmallStorageRTTI rtti_;
435 char buffer_[ANY_SMALL_SPACE_SIZE];
440 const std::type_info* info_;
441 BigStorageRTTI rtti_;
可储存单个任意对象的容器
Definition: Any.h:32
_Ty Cast()
转换为指定类型
Definition: Any.h:154
const _Ty * CastPtr() const noexcept
转换为指定类型的指针
Definition: Any.h:131
const std::type_info & GetType() const noexcept
获取含有对象类型
Definition: Any.h:76
bool HasValue() const noexcept
是否含有对象
Definition: Any.h:88
_Ty Cast() const
转换为指定类型
Definition: Any.h:170
void Swap(Any &rhs) noexcept
交换容器
Definition: Any.h:106
void Emplace(_Args &&... args)
从参数构造对象
Definition: Any.h:96
void Clear() noexcept
销毁所含对象
Definition: Any.h:115
_Ty * CastPtr() noexcept
转换为指定类型的指针
Definition: Any.h:123