erased_storage.h 2.2 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980
  1. #pragma once
  2. #include <concepts>
  3. #include <memory>
  4. #include <type_traits>
  5. namespace NYT {
  6. ////////////////////////////////////////////////////////////////////////////////
  7. template <size_t MaxByteSize>
  8. class TErasedStorage;
  9. ////////////////////////////////////////////////////////////////////////////////
  10. namespace NDetail {
  11. template <class T>
  12. struct TIsErasedStorage
  13. : public std::false_type
  14. { };
  15. template <size_t N>
  16. struct TIsErasedStorage<TErasedStorage<N>>
  17. : public std::true_type
  18. { };
  19. } // namespace NDetail
  20. ////////////////////////////////////////////////////////////////////////////////
  21. template <class T, size_t ErasedStorageMaxByteSize>
  22. concept CTriviallyErasable =
  23. std::default_initializable<T> &&
  24. std::is_trivially_destructible_v<T> &&
  25. std::is_trivially_copyable_v<T> &&
  26. (sizeof(T) <= ErasedStorageMaxByteSize) &&
  27. (alignof(T) <= ErasedStorageMaxByteSize) &&
  28. !std::is_reference_v<T> &&
  29. !NDetail::TIsErasedStorage<T>::value;
  30. ////////////////////////////////////////////////////////////////////////////////
  31. // This class does not call dtor of erased object
  32. // thus we require trivial destructability.
  33. template <size_t MaxByteSize>
  34. class TErasedStorage
  35. {
  36. public:
  37. static constexpr size_t ByteSize = MaxByteSize;
  38. template <CTriviallyErasable<MaxByteSize> TDecayedConcrete>
  39. explicit TErasedStorage(TDecayedConcrete concrete) noexcept;
  40. TErasedStorage(const TErasedStorage& other) = default;
  41. TErasedStorage& operator=(const TErasedStorage& other) = default;
  42. template <CTriviallyErasable<MaxByteSize> TDecayedConcrete>
  43. TDecayedConcrete& AsConcrete() & noexcept;
  44. template <CTriviallyErasable<MaxByteSize> TDecayedConcrete>
  45. const TDecayedConcrete& AsConcrete() const & noexcept;
  46. template <CTriviallyErasable<MaxByteSize> TDecayedConcrete>
  47. TDecayedConcrete&& AsConcrete() && noexcept;
  48. bool operator==(const TErasedStorage& other) const = default;
  49. private:
  50. // NB(arkady-e1ppa): aligned_storage is deprecated.
  51. alignas(MaxByteSize) std::byte Bytes_[MaxByteSize];
  52. };
  53. ////////////////////////////////////////////////////////////////////////////////
  54. } // namespace NYT
  55. #define ERASED_STORAGE_INL_H_
  56. #include "erased_storage-inl.h"
  57. #undef ERASED_STORAGE_INL_H_