1 // Copyright 2017 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 5 #ifndef COMPONENTS_ZUCCHINI_TYPED_VALUE_H_ 6 #define COMPONENTS_ZUCCHINI_TYPED_VALUE_H_ 7 8 #include <ostream> 9 10 namespace zucchini { 11 12 // Strong typed values, with compare and convert functions for underlying data. 13 // Typically one would use strongly typed enums for this. However, for Zucchini, 14 // the number of bytes is not fixed, and must be represented as an integer for 15 // iteration. 16 // |Tag| is a type tag used to uniquely identify TypedValue. 17 // |T| is an integral type used to hold values. 18 // Example: 19 // struct Foo : TypedValue<Foo, int> { 20 // using Foo::TypedValue::TypedValue; // inheriting constructor. 21 // }; 22 // Foo will be used to hold values of type |int|, but with a distinct type from 23 // any other TypedValue. 24 template <class Tag, class T> 25 class TypedValue { 26 public: 27 constexpr TypedValue() = default; TypedValue(const T & value)28 explicit constexpr TypedValue(const T& value) : value_(value) {} 29 T()30 explicit operator T() const { return value_; } value()31 const T value() const { return value_; } 32 33 friend bool operator==(const TypedValue& a, const TypedValue& b) { 34 return a.value_ == b.value_; 35 } 36 friend bool operator!=(const TypedValue& a, const TypedValue& b) { 37 return !(a == b); 38 } 39 friend bool operator<(const TypedValue& a, const TypedValue& b) { 40 return a.value_ < b.value_; 41 } 42 friend bool operator>(const TypedValue& a, const TypedValue& b) { 43 return b < a; 44 } 45 46 private: 47 T value_ = {}; 48 }; 49 50 template <class Tag, class T> 51 std::ostream& operator<<(std::ostream& os, const TypedValue<Tag, T>& tag) { 52 return os << tag.value(); 53 } 54 55 } // namespace zucchini 56 57 #endif // COMPONENTS_ZUCCHINI_TYPED_VALUE_H_ 58