///////////////////////////////////////////////////////////////////////////////
// Comparisons.
-template<class V>
-bool operator==(const Optional<V>& a, const V& b) {
+template <class U, class V>
+bool operator==(const Optional<U>& a, const V& b) {
return a.hasValue() && a.value() == b;
}
-template<class V>
-bool operator!=(const Optional<V>& a, const V& b) {
+template <class U, class V>
+bool operator!=(const Optional<U>& a, const V& b) {
return !(a == b);
}
-template<class V>
-bool operator==(const V& a, const Optional<V>& b) {
+template <class U, class V>
+bool operator==(const U& a, const Optional<V>& b) {
return b.hasValue() && b.value() == a;
}
-template<class V>
-bool operator!=(const V& a, const Optional<V>& b) {
+template <class U, class V>
+bool operator!=(const U& a, const Optional<V>& b) {
return !(a == b);
}
-template<class V>
-bool operator==(const Optional<V>& a, const Optional<V>& b) {
+template <class U, class V>
+bool operator==(const Optional<U>& a, const Optional<V>& b) {
if (a.hasValue() != b.hasValue()) { return false; }
if (a.hasValue()) { return a.value() == b.value(); }
return true;
}
-template<class V>
-bool operator!=(const Optional<V>& a, const Optional<V>& b) {
+template <class U, class V>
+bool operator!=(const Optional<U>& a, const Optional<V>& b) {
return !(a == b);
}
-template<class V>
-bool operator< (const Optional<V>& a, const Optional<V>& b) {
+template <class U, class V>
+bool operator<(const Optional<U>& a, const Optional<V>& b) {
if (a.hasValue() != b.hasValue()) { return a.hasValue() < b.hasValue(); }
if (a.hasValue()) { return a.value() < b.value(); }
return false;
}
-template<class V>
-bool operator> (const Optional<V>& a, const Optional<V>& b) {
+template <class U, class V>
+bool operator>(const Optional<U>& a, const Optional<V>& b) {
return b < a;
}
-template<class V>
-bool operator<=(const Optional<V>& a, const Optional<V>& b) {
+template <class U, class V>
+bool operator<=(const Optional<U>& a, const Optional<V>& b) {
return !(b < a);
}
-template<class V>
-bool operator>=(const Optional<V>& a, const Optional<V>& b) {
+template <class U, class V>
+bool operator>=(const Optional<U>& a, const Optional<V>& b) {
return !(a < b);
}
EXPECT_FALSE(bob != false);
}
+TEST(Optional, HeterogeneousComparisons) {
+ using opt8 = Optional<uint8_t>;
+ using opt64 = Optional<uint64_t>;
+
+ EXPECT_TRUE(opt8(4) == uint64_t(4));
+ EXPECT_FALSE(opt8(8) == uint64_t(4));
+ EXPECT_FALSE(opt8() == uint64_t(4));
+
+ EXPECT_TRUE(uint64_t(4) == opt8(4));
+ EXPECT_FALSE(uint64_t(4) == opt8(8));
+ EXPECT_FALSE(uint64_t(4) == opt8());
+
+ EXPECT_FALSE(opt8(4) != uint64_t(4));
+ EXPECT_TRUE(opt8(8) != uint64_t(4));
+ EXPECT_TRUE(opt8() != uint64_t(4));
+
+ EXPECT_FALSE(uint64_t(4) != opt8(4));
+ EXPECT_TRUE(uint64_t(4) != opt8(8));
+ EXPECT_TRUE(uint64_t(4) != opt8());
+
+ EXPECT_TRUE(opt8() == opt64());
+ EXPECT_TRUE(opt8(4) == opt64(4));
+ EXPECT_FALSE(opt8(8) == opt64(4));
+ EXPECT_FALSE(opt8() == opt64(4));
+ EXPECT_FALSE(opt8(4) == opt64());
+
+ EXPECT_FALSE(opt8() != opt64());
+ EXPECT_FALSE(opt8(4) != opt64(4));
+ EXPECT_TRUE(opt8(8) != opt64(4));
+ EXPECT_TRUE(opt8() != opt64(4));
+ EXPECT_TRUE(opt8(4) != opt64());
+
+ EXPECT_TRUE(opt8() < opt64(4));
+ EXPECT_TRUE(opt8(4) < opt64(8));
+ EXPECT_FALSE(opt8() < opt64());
+ EXPECT_FALSE(opt8(4) < opt64(4));
+ EXPECT_FALSE(opt8(8) < opt64(4));
+ EXPECT_FALSE(opt8(4) < opt64());
+
+ EXPECT_FALSE(opt8() > opt64(4));
+ EXPECT_FALSE(opt8(4) > opt64(8));
+ EXPECT_FALSE(opt8() > opt64());
+ EXPECT_FALSE(opt8(4) > opt64(4));
+ EXPECT_TRUE(opt8(8) > opt64(4));
+ EXPECT_TRUE(opt8(4) > opt64());
+
+ EXPECT_TRUE(opt8() <= opt64(4));
+ EXPECT_TRUE(opt8(4) <= opt64(8));
+ EXPECT_TRUE(opt8() <= opt64());
+ EXPECT_TRUE(opt8(4) <= opt64(4));
+ EXPECT_FALSE(opt8(8) <= opt64(4));
+ EXPECT_FALSE(opt8(4) <= opt64());
+
+ EXPECT_FALSE(opt8() >= opt64(4));
+ EXPECT_FALSE(opt8(4) >= opt64(8));
+ EXPECT_TRUE(opt8() >= opt64());
+ EXPECT_TRUE(opt8(4) >= opt64(4));
+ EXPECT_TRUE(opt8(8) >= opt64(4));
+ EXPECT_TRUE(opt8(4) >= opt64());
+}
+
TEST(Optional, Conversions) {
Optional<bool> mbool;
Optional<short> mshort;