1 // Copyright 2019 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 #ifndef V8_CRDTP_MAYBE_H_ 5 #define V8_CRDTP_MAYBE_H_ 6 7 #include <cassert> 8 #include <memory> 9 10 namespace v8_crdtp { 11 12 // ============================================================================= 13 // detail::PtrMaybe, detail::ValueMaybe, templates for optional 14 // pointers / values which are used in ../lib/Forward_h.template. 15 // ============================================================================= 16 17 namespace detail { 18 template <typename T> 19 class PtrMaybe { 20 public: 21 PtrMaybe() = default; PtrMaybe(std::unique_ptr<T> value)22 PtrMaybe(std::unique_ptr<T> value) : value_(std::move(value)) {} PtrMaybe(PtrMaybe && other)23 PtrMaybe(PtrMaybe&& other) noexcept : value_(std::move(other.value_)) {} 24 void operator=(std::unique_ptr<T> value) { value_ = std::move(value); } fromJust()25 T* fromJust() const { 26 assert(value_); 27 return value_.get(); 28 } fromMaybe(T * default_value)29 T* fromMaybe(T* default_value) const { 30 return value_ ? value_.get() : default_value; 31 } isJust()32 bool isJust() const { return value_ != nullptr; } takeJust()33 std::unique_ptr<T> takeJust() { 34 assert(value_); 35 return std::move(value_); 36 } 37 38 private: 39 std::unique_ptr<T> value_; 40 }; 41 42 template <typename T> 43 class ValueMaybe { 44 public: ValueMaybe()45 ValueMaybe() : is_just_(false), value_() {} ValueMaybe(T value)46 ValueMaybe(T value) : is_just_(true), value_(std::move(value)) {} ValueMaybe(ValueMaybe && other)47 ValueMaybe(ValueMaybe&& other) noexcept 48 : is_just_(other.is_just_), value_(std::move(other.value_)) {} 49 void operator=(T value) { 50 value_ = value; 51 is_just_ = true; 52 } fromJust()53 const T& fromJust() const { 54 assert(is_just_); 55 return value_; 56 } fromMaybe(const T & default_value)57 const T& fromMaybe(const T& default_value) const { 58 return is_just_ ? value_ : default_value; 59 } isJust()60 bool isJust() const { return is_just_; } takeJust()61 T takeJust() { 62 assert(is_just_); 63 is_just_ = false; 64 return std::move(value_); 65 } 66 67 private: 68 bool is_just_; 69 T value_; 70 }; 71 72 template <typename T> 73 struct MaybeTypedef { 74 typedef PtrMaybe<T> type; 75 }; 76 77 template <> 78 struct MaybeTypedef<bool> { 79 typedef ValueMaybe<bool> type; 80 }; 81 82 template <> 83 struct MaybeTypedef<int> { 84 typedef ValueMaybe<int> type; 85 }; 86 87 template <> 88 struct MaybeTypedef<double> { 89 typedef ValueMaybe<double> type; 90 }; 91 92 template <> 93 struct MaybeTypedef<std::string> { 94 typedef ValueMaybe<std::string> type; 95 }; 96 97 } // namespace detail 98 99 template <typename T> 100 using Maybe = typename detail::MaybeTypedef<T>::type; 101 102 } // namespace v8_crdtp 103 104 #endif // V8_CRDTP_MAYBE_H_ 105