From 6aa664eeefab8a3ab1ca770f9299041f320f7504 Mon Sep 17 00:00:00 2001 From: Drew Noakes Date: Fri, 31 Oct 2014 10:59:35 +0000 Subject: [PATCH] Document traits of types using and static_assert in tests. The tests state the current traits of types Document, Value and StringBuffer. There are slight differences between them. It seems like a good idea to extend this approach across more types, and to review the expected traits across the board. --- test/unittest/documenttest.cpp | 33 ++++++++++++++++++++++++++---- test/unittest/stringbuffertest.cpp | 33 +++++++++++++++++++++++++++--- test/unittest/valuetest.cpp | 32 +++++++++++++++++++++++++++-- 3 files changed, 89 insertions(+), 9 deletions(-) diff --git a/test/unittest/documenttest.cpp b/test/unittest/documenttest.cpp index f5e1b50..250d67b 100644 --- a/test/unittest/documenttest.cpp +++ b/test/unittest/documenttest.cpp @@ -229,6 +229,31 @@ TEST(Document, UTF16_Document) { #if RAPIDJSON_HAS_CXX11_RVALUE_REFS +#include + +TEST(Document, Traits) { + static_assert( std::is_constructible::value, ""); + static_assert( std::is_default_constructible::value, ""); + static_assert(!std::is_copy_constructible::value, ""); + static_assert( std::is_move_constructible::value, ""); + + static_assert(!std::is_nothrow_constructible::value, ""); + static_assert(!std::is_nothrow_default_constructible::value, ""); + static_assert(!std::is_nothrow_copy_constructible::value, ""); + static_assert( std::is_nothrow_move_constructible::value, ""); + + static_assert( std::is_assignable::value, ""); + static_assert(!std::is_copy_assignable::value, ""); + static_assert( std::is_move_assignable::value, ""); + + static_assert( std::is_nothrow_assignable::value, ""); + static_assert(!std::is_nothrow_copy_assignable::value, ""); + static_assert( std::is_nothrow_move_assignable::value, ""); + + static_assert( std::is_destructible::value, ""); + static_assert( std::is_nothrow_destructible::value, ""); +} + template struct DocumentMove: public ::testing::Test { }; @@ -248,7 +273,7 @@ TYPED_TEST(DocumentMove, MoveConstructor) { EXPECT_EQ(3u, a.Size()); EXPECT_EQ(&a.GetAllocator(), &allocator); - // Document b(a); // should not compile + // Document b(a); // does not compile (!is_copy_constructible) Document b(std::move(a)); EXPECT_TRUE(a.IsNull()); EXPECT_TRUE(b.IsArray()); @@ -261,7 +286,7 @@ TYPED_TEST(DocumentMove, MoveConstructor) { EXPECT_TRUE(b.IsObject()); EXPECT_EQ(2u, b.MemberCount()); - // Document c = a; // should not compile + // Document c = a; // does not compile (!is_copy_constructible) Document c = std::move(b); EXPECT_TRUE(b.IsNull()); EXPECT_TRUE(c.IsObject()); @@ -336,7 +361,7 @@ TYPED_TEST(DocumentMove, MoveAssignment) { EXPECT_EQ(3u, a.Size()); EXPECT_EQ(&a.GetAllocator(), &allocator); - // Document b; b = a; // should not compile + // Document b; b = a; // does not compile (!is_copy_assignable) Document b; b = std::move(a); EXPECT_TRUE(a.IsNull()); @@ -350,7 +375,7 @@ TYPED_TEST(DocumentMove, MoveAssignment) { EXPECT_TRUE(b.IsObject()); EXPECT_EQ(2u, b.MemberCount()); - // Document c; c = a; // should not compile + // Document c; c = a; // does not compile (see static_assert) Document c; c = std::move(b); EXPECT_TRUE(b.IsNull()); diff --git a/test/unittest/stringbuffertest.cpp b/test/unittest/stringbuffertest.cpp index 5e3c092..b808ac5 100644 --- a/test/unittest/stringbuffertest.cpp +++ b/test/unittest/stringbuffertest.cpp @@ -70,6 +70,32 @@ TEST(StringBuffer, Pop) { } #if RAPIDJSON_HAS_CXX11_RVALUE_REFS + +#include + +TEST(StringBuffer, Traits) { + static_assert( std::is_constructible::value, ""); + static_assert( std::is_default_constructible::value, ""); + static_assert(!std::is_copy_constructible::value, ""); + static_assert( std::is_move_constructible::value, ""); + + static_assert(!std::is_nothrow_constructible::value, ""); + static_assert(!std::is_nothrow_default_constructible::value, ""); + static_assert(!std::is_nothrow_copy_constructible::value, ""); + static_assert(!std::is_nothrow_move_constructible::value, ""); + + static_assert( std::is_assignable::value, ""); + static_assert(!std::is_copy_assignable::value, ""); + static_assert( std::is_move_assignable::value, ""); + + static_assert(!std::is_nothrow_assignable::value, ""); + static_assert(!std::is_nothrow_copy_assignable::value, ""); + static_assert(!std::is_nothrow_move_assignable::value, ""); + + static_assert( std::is_destructible::value, ""); + static_assert( std::is_nothrow_destructible::value, ""); +} + TEST(StringBuffer, MoveConstructor) { StringBuffer x; x.Put('A'); @@ -80,13 +106,13 @@ TEST(StringBuffer, MoveConstructor) { EXPECT_EQ(4u, x.GetSize()); EXPECT_STREQ("ABCD", x.GetString()); - // StringBuffer y(x); // should not compile + // StringBuffer y(x); // does not compile (!is_copy_constructible) StringBuffer y(std::move(x)); EXPECT_EQ(0u, x.GetSize()); EXPECT_EQ(4u, y.GetSize()); EXPECT_STREQ("ABCD", y.GetString()); - // StringBuffer z = y; // should not compile + // StringBuffer z = y; // does not compile (!is_copy_assignable) StringBuffer z = std::move(y); EXPECT_EQ(0u, y.GetSize()); EXPECT_EQ(4u, z.GetSize()); @@ -104,10 +130,11 @@ TEST(StringBuffer, MoveAssignment) { EXPECT_STREQ("ABCD", x.GetString()); StringBuffer y; - // y = x; // should not compile + // y = x; // does not compile (!is_copy_assignable) y = std::move(x); EXPECT_EQ(0u, x.GetSize()); EXPECT_EQ(4u, y.GetSize()); EXPECT_STREQ("ABCD", y.GetString()); } + #endif // RAPIDJSON_HAS_CXX11_RVALUE_REFS diff --git a/test/unittest/valuetest.cpp b/test/unittest/valuetest.cpp index 6dc6c87..1f3ffe8 100644 --- a/test/unittest/valuetest.cpp +++ b/test/unittest/valuetest.cpp @@ -39,6 +39,33 @@ TEST(Value, DefaultConstructor) { //} #if RAPIDJSON_HAS_CXX11_RVALUE_REFS + +#include + +TEST(Value, Traits) { + typedef GenericValue, CrtAllocator> Value; + static_assert( std::is_constructible::value, ""); + static_assert( std::is_default_constructible::value, ""); + static_assert(!std::is_copy_constructible::value, ""); + static_assert( std::is_move_constructible::value, ""); + + static_assert( std::is_nothrow_constructible::value, ""); + static_assert( std::is_nothrow_default_constructible::value, ""); + static_assert(!std::is_nothrow_copy_constructible::value, ""); + static_assert( std::is_nothrow_move_constructible::value, ""); + + static_assert( std::is_assignable::value, ""); + static_assert(!std::is_copy_assignable::value, ""); + static_assert( std::is_move_assignable::value, ""); + + static_assert( std::is_nothrow_assignable::value, ""); + static_assert(!std::is_nothrow_copy_assignable::value, ""); + static_assert( std::is_nothrow_move_assignable::value, ""); + + static_assert( std::is_destructible::value, ""); + static_assert( std::is_nothrow_destructible::value, ""); +} + TEST(Value, MoveConstructor) { typedef GenericValue, CrtAllocator> Value; Value::AllocatorType allocator; @@ -49,18 +76,19 @@ TEST(Value, MoveConstructor) { EXPECT_TRUE(x.IsArray()); EXPECT_EQ(4u, x.Size()); - // Value y(x); // should not compile + // Value y(x); // does not compile (!is_copy_constructible) Value y(std::move(x)); EXPECT_TRUE(x.IsNull()); EXPECT_TRUE(y.IsArray()); EXPECT_EQ(4u, y.Size()); - // Value z = y; // should not compile + // Value z = y; // does not compile (!is_copy_assignable) Value z = std::move(y); EXPECT_TRUE(y.IsNull()); EXPECT_TRUE(z.IsArray()); EXPECT_EQ(4u, z.Size()); } + #endif // RAPIDJSON_HAS_CXX11_RVALUE_REFS TEST(Value, AssignmentOperator) {