diff --git a/test/optional_test_noexcept_move.cpp b/test/optional_test_noexcept_move.cpp index e072785..b0c2220 100644 --- a/test/optional_test_noexcept_move.cpp +++ b/test/optional_test_noexcept_move.cpp @@ -41,6 +41,7 @@ struct NothrowNone { void operator=(NothrowNone&&) BOOST_NOEXCEPT_IF(false) {}; }; +#if 0 // these also test type_traits, which are wrong void test_noexcept_as_defined() // this is a compile-time test { BOOST_STATIC_ASSERT(::boost::is_nothrow_move_constructible::value); @@ -56,7 +57,7 @@ void test_noexcept_as_defined() // this is a compile-time test BOOST_STATIC_ASSERT(!::boost::is_nothrow_move_assignable::value); } -void test_noexcept_on_optional() // this is a compile-time test +void test_noexcept_on_optional_with_type_traits() // this is a compile-time test { BOOST_STATIC_ASSERT(::boost::is_nothrow_move_constructible >::value); BOOST_STATIC_ASSERT(::boost::is_nothrow_move_assignable >::value); @@ -74,6 +75,35 @@ void test_noexcept_on_optional() // this is a compile-time test BOOST_STATIC_ASSERT(!::boost::is_nothrow_move_assignable >::value); BOOST_STATIC_ASSERT(BOOST_NOEXCEPT_EXPR(optional())); } +#endif + +void test_noexcept_optional_with_operator() // compile-time test +{ + typedef optional ONx2; + typedef optional ONxC; + typedef optional ONxA; + typedef optional ONx0; + ONx2 onx2; + ONxC onxC; + ONxA onxA; + ONx0 onx0; + + BOOST_STATIC_ASSERT( BOOST_NOEXCEPT_EXPR( ONx2() )); + BOOST_STATIC_ASSERT( BOOST_NOEXCEPT_EXPR( ONx2(boost::move(onx2)) )); + BOOST_STATIC_ASSERT( BOOST_NOEXCEPT_EXPR( onx2 = ONx2() )); + + BOOST_STATIC_ASSERT( BOOST_NOEXCEPT_EXPR( ONxC() )); + BOOST_STATIC_ASSERT( BOOST_NOEXCEPT_EXPR( ONxC(boost::move(onxC)) )); + BOOST_STATIC_ASSERT(!BOOST_NOEXCEPT_EXPR( onxC = ONxC() )); + + BOOST_STATIC_ASSERT( BOOST_NOEXCEPT_EXPR( ONxA() )); + BOOST_STATIC_ASSERT(!BOOST_NOEXCEPT_EXPR( ONxA(boost::move(onxA)) )); + BOOST_STATIC_ASSERT(!BOOST_NOEXCEPT_EXPR( onxA = ONxA() )); + + BOOST_STATIC_ASSERT( BOOST_NOEXCEPT_EXPR( ONx0() )); + BOOST_STATIC_ASSERT(!BOOST_NOEXCEPT_EXPR( ONx0(boost::move(onx0)) )); + BOOST_STATIC_ASSERT(!BOOST_NOEXCEPT_EXPR( onx0 = ONx0() )); +} #endif // !defned BOOST_NO_NOEXCEPT #endif // !defined BOOST_NO_CXX11_RVALUE_REFERENCES diff --git a/test/optional_test_ref_portable_minimum.cpp b/test/optional_test_ref_portable_minimum.cpp index 4439d8c..6f4ed9a 100644 --- a/test/optional_test_ref_portable_minimum.cpp +++ b/test/optional_test_ref_portable_minimum.cpp @@ -28,6 +28,7 @@ struct ScopeGuard // no copy/move ctor/assign int val_; explicit ScopeGuard(int v) : val_(v) {} int& val() { return val_; } + const int& val() const { return val_; } private: ScopeGuard(ScopeGuard const&); @@ -37,6 +38,7 @@ private: struct Abstract { virtual int& val() = 0; + virtual const int& val() const = 0; virtual ~Abstract() {} Abstract(){} @@ -50,6 +52,7 @@ struct Impl : Abstract int val_; Impl(int v) : val_(v) {} int& val() { return val_; } + const int& val() const { return val_; } }; template @@ -80,6 +83,11 @@ int& val(int& i) { return i; } int& val(Abstract& a) { return a.val(); } int& val(ScopeGuard& g) { return g.val(); } +bool operator==(const Abstract& l, const Abstract& r) { return l.val() == r.val(); } +bool operator==(const ScopeGuard& l, const ScopeGuard& r) { return l.val() == r.val(); } + +bool operator<(const Abstract& l, const Abstract& r) { return l.val() < r.val(); } +bool operator<(const ScopeGuard& l, const ScopeGuard& r) { return l.val() < r.val(); } // end testable classes template @@ -222,6 +230,193 @@ void test_rebinding_assignment_semantics() BOOST_TEST_EQ(val(v), 2); } +template +void test_equality() +{ + typename concrete_type_of::type v1(1), v2(2), v2_(2), v3(3); + optional o1(v1), o2(v2), o2_(v2_), o3(v3), o3_(v3), oN, oN_; + // o2 and o2_ point to different objects; o3 and o3_ point to the same object + + BOOST_TEST(oN == oN); + BOOST_TEST(oN == oN_); + BOOST_TEST(oN_ == oN); + BOOST_TEST(o1 == o1); + BOOST_TEST(o2 == o2); + BOOST_TEST(o2 == o2_); + BOOST_TEST(o2_ == o2); + BOOST_TEST(o3 == o3); + BOOST_TEST(o3 == o3_); + BOOST_TEST(!(oN == o1)); + BOOST_TEST(!(o1 == oN)); + BOOST_TEST(!(o2 == o1)); + BOOST_TEST(!(o2 == oN)); + + BOOST_TEST(!(oN != oN)); + BOOST_TEST(!(oN != oN_)); + BOOST_TEST(!(oN_ != oN)); + BOOST_TEST(!(o1 != o1)); + BOOST_TEST(!(o2 != o2)); + BOOST_TEST(!(o2 != o2_)); + BOOST_TEST(!(o2_ != o2)); + BOOST_TEST(!(o3 != o3)); + BOOST_TEST(!(o3 != o3_)); + BOOST_TEST( (oN != o1)); + BOOST_TEST( (o1 != oN)); + BOOST_TEST( (o2 != o1)); + BOOST_TEST( (o2 != oN)); +} + +template +void test_order() +{ + typename concrete_type_of::type v1(1), v2(2), v2_(2), v3(3); + optional o1(v1), o2(v2), o2_(v2_), o3(v3), o3_(v3), oN, oN_; + // o2 and o2_ point to different objects; o3 and o3_ point to the same object + + BOOST_TEST(!(oN < oN)); + BOOST_TEST(!(oN < oN_)); + BOOST_TEST(!(oN_ < oN)); + BOOST_TEST(!(o1 < o1)); + BOOST_TEST(!(o2 < o2)); + BOOST_TEST(!(o2 < o2_)); + BOOST_TEST(!(o2_ < o2)); + BOOST_TEST(!(o3 < o3)); + BOOST_TEST(!(o3 < o3_)); + + BOOST_TEST( (oN <= oN)); + BOOST_TEST( (oN <= oN_)); + BOOST_TEST( (oN_ <= oN)); + BOOST_TEST( (o1 <= o1)); + BOOST_TEST( (o2 <= o2)); + BOOST_TEST( (o2 <= o2_)); + BOOST_TEST( (o2_ <= o2)); + BOOST_TEST( (o3 <= o3)); + BOOST_TEST( (o3 <= o3_)); + + BOOST_TEST(!(oN > oN)); + BOOST_TEST(!(oN > oN_)); + BOOST_TEST(!(oN_ > oN)); + BOOST_TEST(!(o1 > o1)); + BOOST_TEST(!(o2 > o2)); + BOOST_TEST(!(o2 > o2_)); + BOOST_TEST(!(o2_ > o2)); + BOOST_TEST(!(o3 > o3)); + BOOST_TEST(!(o3 > o3_)); + + BOOST_TEST( (oN >= oN)); + BOOST_TEST( (oN >= oN_)); + BOOST_TEST( (oN_ >= oN)); + BOOST_TEST( (o1 >= o1)); + BOOST_TEST( (o2 >= o2)); + BOOST_TEST( (o2 >= o2_)); + BOOST_TEST( (o2_ >= o2)); + BOOST_TEST( (o3 >= o3)); + BOOST_TEST( (o3 >= o3_)); + + BOOST_TEST( (oN < o1)); + BOOST_TEST( (oN_ < o1)); + BOOST_TEST( (oN < o2)); + BOOST_TEST( (oN_ < o2)); + BOOST_TEST( (oN < o2_)); + BOOST_TEST( (oN_ < o2_)); + BOOST_TEST( (oN < o3)); + BOOST_TEST( (oN_ < o3)); + BOOST_TEST( (oN < o3_)); + BOOST_TEST( (oN_ < o3_)); + BOOST_TEST( (o1 < o2)); + BOOST_TEST( (o1 < o2_)); + BOOST_TEST( (o1 < o3)); + BOOST_TEST( (o1 < o3_)); + BOOST_TEST( (o2 < o3)); + BOOST_TEST( (o2_ < o3)); + BOOST_TEST( (o2 < o3_)); + BOOST_TEST( (o2_ < o3_)); + + BOOST_TEST( (oN <= o1)); + BOOST_TEST( (oN_ <= o1)); + BOOST_TEST( (oN <= o2)); + BOOST_TEST( (oN_ <= o2)); + BOOST_TEST( (oN <= o2_)); + BOOST_TEST( (oN_ <= o2_)); + BOOST_TEST( (oN <= o3)); + BOOST_TEST( (oN_ <= o3)); + BOOST_TEST( (oN <= o3_)); + BOOST_TEST( (oN_ <= o3_)); + BOOST_TEST( (o1 <= o2)); + BOOST_TEST( (o1 <= o2_)); + BOOST_TEST( (o1 <= o3)); + BOOST_TEST( (o1 <= o3_)); + BOOST_TEST( (o2 <= o3)); + BOOST_TEST( (o2_ <= o3)); + BOOST_TEST( (o2 <= o3_)); + BOOST_TEST( (o2_ <= o3_)); + + BOOST_TEST(!(oN > o1)); + BOOST_TEST(!(oN_ > o1)); + BOOST_TEST(!(oN > o2)); + BOOST_TEST(!(oN_ > o2)); + BOOST_TEST(!(oN > o2_)); + BOOST_TEST(!(oN_ > o2_)); + BOOST_TEST(!(oN > o3)); + BOOST_TEST(!(oN_ > o3)); + BOOST_TEST(!(oN > o3_)); + BOOST_TEST(!(oN_ > o3_)); + BOOST_TEST(!(o1 > o2)); + BOOST_TEST(!(o1 > o2_)); + BOOST_TEST(!(o1 > o3)); + BOOST_TEST(!(o1 > o3_)); + BOOST_TEST(!(o2 > o3)); + BOOST_TEST(!(o2_ > o3)); + BOOST_TEST(!(o2 > o3_)); + BOOST_TEST(!(o2_ > o3_)); + + BOOST_TEST(!(oN >= o1)); + BOOST_TEST(!(oN_ >= o1)); + BOOST_TEST(!(oN >= o2)); + BOOST_TEST(!(oN_ >= o2)); + BOOST_TEST(!(oN >= o2_)); + BOOST_TEST(!(oN_ >= o2_)); + BOOST_TEST(!(oN >= o3)); + BOOST_TEST(!(oN_ >= o3)); + BOOST_TEST(!(oN >= o3_)); + BOOST_TEST(!(oN_ >= o3_)); + BOOST_TEST(!(o1 >= o2)); + BOOST_TEST(!(o1 >= o2_)); + BOOST_TEST(!(o1 >= o3)); + BOOST_TEST(!(o1 >= o3_)); + BOOST_TEST(!(o2 >= o3)); + BOOST_TEST(!(o2_ >= o3)); + BOOST_TEST(!(o2 >= o3_)); + BOOST_TEST(!(o2_ >= o3_)); + + BOOST_TEST(!(o1 < oN)); + BOOST_TEST(!(o1 < oN_)); + BOOST_TEST(!(o2 < oN)); + BOOST_TEST(!(o2 < oN_)); + BOOST_TEST(!(o2_ < oN)); + BOOST_TEST(!(o2_ < oN_)); + BOOST_TEST(!(o3 < oN)); + BOOST_TEST(!(o3 < oN_)); + BOOST_TEST(!(o3_ < oN)); + BOOST_TEST(!(o3_ < oN_)); + BOOST_TEST(!(o2 < oN)); + BOOST_TEST(!(o2_ < oN_)); + BOOST_TEST(!(o3 < oN)); + BOOST_TEST(!(o3_ < oN_)); + BOOST_TEST(!(o3 < oN)); + BOOST_TEST(!(o3 < oN_)); + BOOST_TEST(!(o3_ < oN)); + BOOST_TEST(!(o3_ < oN_)); +} + +template +void test_swap() +{ + typename concrete_type_of::type v1(1), v2(2); + optional o1(v1), o1_(v1), o2(v2), o2_(v2), oN, oN_; + + // swap(o1, o1); DOESN'T WORK +} template void test_optional_ref() @@ -232,6 +427,9 @@ void test_optional_ref() test_rebinding_assignment_semantics(); test_clearing_the_value(); test_arrow(); + test_equality(); + test_order(); + test_swap(); } int main()