Some improvements to the nullable interface
This commit is contained in:
parent
248ad447b1
commit
85be7c32a4
@ -95,37 +95,42 @@ namespace cpptrace {
|
||||
// use.
|
||||
template<typename T, typename std::enable_if<std::is_integral<T>::value, int>::type = 0>
|
||||
struct nullable {
|
||||
T raw_value;
|
||||
nullable& operator=(T value) {
|
||||
T raw_value = null_value();
|
||||
constexpr nullable() noexcept = default;
|
||||
constexpr nullable(T value) noexcept : raw_value(value) {}
|
||||
constexpr nullable& operator=(T value) noexcept {
|
||||
raw_value = value;
|
||||
return *this;
|
||||
}
|
||||
bool has_value() const noexcept {
|
||||
return raw_value != (std::numeric_limits<T>::max)();
|
||||
constexpr bool has_value() const noexcept {
|
||||
return raw_value != null_value();
|
||||
}
|
||||
T& value() noexcept {
|
||||
constexpr T& value() noexcept {
|
||||
return raw_value;
|
||||
}
|
||||
const T& value() const noexcept {
|
||||
constexpr const T& value() const noexcept {
|
||||
return raw_value;
|
||||
}
|
||||
T value_or(T alternative) const noexcept {
|
||||
constexpr T value_or(T alternative) const noexcept {
|
||||
return has_value() ? raw_value : alternative;
|
||||
}
|
||||
void swap(nullable& other) noexcept {
|
||||
constexpr void swap(nullable& other) noexcept {
|
||||
std::swap(raw_value, other.raw_value);
|
||||
}
|
||||
void reset() noexcept {
|
||||
constexpr void reset() noexcept {
|
||||
raw_value = (std::numeric_limits<T>::max)();
|
||||
}
|
||||
bool operator==(const nullable& other) const noexcept {
|
||||
constexpr bool operator==(const nullable& other) const noexcept {
|
||||
return raw_value == other.raw_value;
|
||||
}
|
||||
bool operator!=(const nullable& other) const noexcept {
|
||||
constexpr bool operator!=(const nullable& other) const noexcept {
|
||||
return raw_value != other.raw_value;
|
||||
}
|
||||
constexpr static T null_value() noexcept {
|
||||
return (std::numeric_limits<T>::max)();
|
||||
}
|
||||
constexpr static nullable null() noexcept {
|
||||
return { (std::numeric_limits<T>::max)() };
|
||||
return { null_value() };
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@ -13,20 +13,26 @@ TEST(NullableTest, Basic) {
|
||||
nullable<std::uint32_t> a{12};
|
||||
EXPECT_EQ(a.value(), 12);
|
||||
EXPECT_EQ(a.raw_value, 12);
|
||||
// TODO: =
|
||||
nullable<std::uint32_t> b = 20;
|
||||
EXPECT_EQ(b.value(), 20);
|
||||
}
|
||||
|
||||
TEST(NullableTest, Null) {
|
||||
auto a = nullable<std::uint32_t>::null();
|
||||
EXPECT_FALSE(a.has_value());
|
||||
EXPECT_EQ(a.raw_value, (std::numeric_limits<std::uint32_t>::max)());
|
||||
// TODO: default construct
|
||||
nullable<std::uint32_t> b;
|
||||
EXPECT_FALSE(b.has_value());
|
||||
EXPECT_EQ(b.raw_value, nullable<std::uint32_t>::null_value());
|
||||
}
|
||||
|
||||
TEST(NullableTest, Assignment) {
|
||||
nullable<std::uint32_t> a;
|
||||
a = 12;
|
||||
EXPECT_EQ(a.value(), 12);
|
||||
nullable<std::uint32_t> b = 20;
|
||||
a = b;
|
||||
EXPECT_EQ(a.value(), 20);
|
||||
}
|
||||
|
||||
TEST(NullableTest, Reset) {
|
||||
@ -49,7 +55,7 @@ TEST(NullableTest, Comparison) {
|
||||
|
||||
TEST(NullableTest, Swap) {
|
||||
auto a = nullable<std::uint32_t>::null();
|
||||
nullable<std::uint32_t> b{12};
|
||||
nullable<std::uint32_t> b = 12;
|
||||
EXPECT_FALSE(a.has_value());
|
||||
EXPECT_EQ(b.value(), 12);
|
||||
a.swap(b);
|
||||
|
||||
Loading…
Reference in New Issue
Block a user