123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116 |
- #pragma once
- #include <utility>
- #include "ptr.h"
- template <class TBase, class TCounter>
- struct TWithRefCount: public TBase, public TRefCounted<TWithRefCount<TBase, TCounter>, TCounter> {
- using TBase::TBase;
- };
- template <class T>
- struct TPtrPolicy {
- inline TPtrPolicy(T* t Y_LIFETIME_BOUND)
- : T_(t)
- {
- }
- inline T* Ptr() noexcept {
- return T_;
- }
- inline const T* Ptr() const noexcept {
- return T_;
- }
- T* T_;
- };
- template <class T>
- struct TEmbedPolicy {
- template <typename... Args, typename = typename std::enable_if<std::is_constructible<T, Args...>::value>::type>
- inline TEmbedPolicy(Args&&... args)
- : T_(std::forward<Args>(args)...)
- {
- }
- inline T* Ptr() noexcept {
- return &T_;
- }
- inline const T* Ptr() const noexcept {
- return &T_;
- }
- T T_;
- };
- template <class T, class TCounter>
- struct TRefPolicy {
- using THelper = TWithRefCount<T, TCounter>;
- template <typename... Args, typename = typename std::enable_if<std::is_constructible<T, Args...>::value>::type>
- inline TRefPolicy(Args&&... args)
- : T_(new THelper(std::forward<Args>(args)...))
- {
- }
- inline T* Ptr() noexcept {
- return T_.Get();
- }
- inline const T* Ptr() const noexcept {
- return T_.Get();
- }
- TIntrusivePtr<THelper> T_;
- };
- /**
- * Storage class that can be handy for implementing proxies / adaptors that can
- * accept both lvalues and rvalues. In the latter case it's often required to
- * extend the lifetime of the passed rvalue, and the only option is to store it
- * in your proxy / adaptor.
- *
- * Example usage:
- * \code
- * template<class T>
- * struct TProxy {
- * TAutoEmbedOrPtrPolicy<T> Value_;
- * // Your proxy code...
- * };
- *
- * template<class T>
- * TProxy<T> MakeProxy(T&& value) {
- * // Rvalues are automagically moved-from, and stored inside the proxy.
- * return {std::forward<T>(value)};
- * }
- * \endcode
- *
- * Look at `Reversed` in `adaptor.h` for real example.
- */
- template <class T, bool IsReference = std::is_reference<T>::value>
- struct TAutoEmbedOrPtrPolicy: TPtrPolicy<std::remove_reference_t<T>> {
- using TBase = TPtrPolicy<std::remove_reference_t<T>>;
- TAutoEmbedOrPtrPolicy(T& reference Y_LIFETIME_BOUND)
- : TBase(&reference)
- {
- }
- };
- template <class T>
- struct TAutoEmbedOrPtrPolicy<T, false>: TEmbedPolicy<T> {
- using TBase = TEmbedPolicy<T>;
- TAutoEmbedOrPtrPolicy(T&& object)
- : TBase(std::move(object))
- {
- }
- };
- template <class T>
- using TAtomicRefPolicy = TRefPolicy<T, TAtomicCounter>;
- template <class T>
- using TSimpleRefPolicy = TRefPolicy<T, TSimpleCounter>;
|