Makes all container matchers work with (possibly multi-dimensional) native arrays; makes Contains() accept a matcher; adds Value(x, m); improves gmock doctor to diagnose the Type in Template Base disease.
This commit is contained in:
		@@ -53,6 +53,7 @@ using std::pair;
 | 
			
		||||
using std::set;
 | 
			
		||||
using std::stringstream;
 | 
			
		||||
using std::vector;
 | 
			
		||||
using std::tr1::make_tuple;
 | 
			
		||||
using testing::_;
 | 
			
		||||
using testing::Contains;
 | 
			
		||||
using testing::ElementsAre;
 | 
			
		||||
@@ -60,6 +61,7 @@ using testing::ElementsAreArray;
 | 
			
		||||
using testing::Eq;
 | 
			
		||||
using testing::Ge;
 | 
			
		||||
using testing::Gt;
 | 
			
		||||
using testing::Lt;
 | 
			
		||||
using testing::MakeMatcher;
 | 
			
		||||
using testing::Matcher;
 | 
			
		||||
using testing::MatcherInterface;
 | 
			
		||||
@@ -69,6 +71,7 @@ using testing::Pointee;
 | 
			
		||||
using testing::Ref;
 | 
			
		||||
using testing::StaticAssertTypeEq;
 | 
			
		||||
using testing::StrEq;
 | 
			
		||||
using testing::Value;
 | 
			
		||||
using testing::internal::string;
 | 
			
		||||
 | 
			
		||||
// Returns the description of the given matcher.
 | 
			
		||||
@@ -330,6 +333,39 @@ TEST(ElementsAreTest, WorksWithContainerPointerUsingPointee) {
 | 
			
		||||
  EXPECT_THAT(&v, Not(Pointee(ElementsAre(0, _, 3))));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ElementsAreTest, WorksWithNativeArrayPassedByReference) {
 | 
			
		||||
  int array[] = { 0, 1, 2 };
 | 
			
		||||
  EXPECT_THAT(array, ElementsAre(0, 1, _));
 | 
			
		||||
  EXPECT_THAT(array, Not(ElementsAre(1, _, _)));
 | 
			
		||||
  EXPECT_THAT(array, Not(ElementsAre(0, _)));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
class NativeArrayPassedAsPointerAndSize {
 | 
			
		||||
 public:
 | 
			
		||||
  MOCK_METHOD2(Helper, void(int* array, int size));
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
TEST(ElementsAreTest, WorksWithNativeArrayPassedAsPointerAndSize) {
 | 
			
		||||
  int array[] = { 0, 1 };
 | 
			
		||||
  ::std::tr1::tuple<int*, size_t> array_as_tuple(array, 2);
 | 
			
		||||
  EXPECT_THAT(array_as_tuple, ElementsAre(0, 1));
 | 
			
		||||
  EXPECT_THAT(array_as_tuple, Not(ElementsAre(0)));
 | 
			
		||||
 | 
			
		||||
  NativeArrayPassedAsPointerAndSize helper;
 | 
			
		||||
  EXPECT_CALL(helper, Helper(_, _))
 | 
			
		||||
      .WithArguments(ElementsAre(0, 1));
 | 
			
		||||
  helper.Helper(array, 2);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ElementsAreTest, WorksWithTwoDimensionalNativeArray) {
 | 
			
		||||
  const char a2[][3] = { "hi", "lo" };
 | 
			
		||||
  EXPECT_THAT(a2, ElementsAre(ElementsAre('h', 'i', '\0'),
 | 
			
		||||
                              ElementsAre('l', 'o', '\0')));
 | 
			
		||||
  EXPECT_THAT(a2, ElementsAre(StrEq("hi"), StrEq("lo")));
 | 
			
		||||
  EXPECT_THAT(a2, ElementsAre(Not(ElementsAre('h', 'o', '\0')),
 | 
			
		||||
                              ElementsAre('l', 'o', '\0')));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests for ElementsAreArray().  Since ElementsAreArray() shares most
 | 
			
		||||
// of the implementation with ElementsAre(), we don't test it as
 | 
			
		||||
// thoroughly here.
 | 
			
		||||
@@ -379,6 +415,17 @@ TEST(ElementsAreArrayTest, CanBeCreatedWithMatcherArray) {
 | 
			
		||||
  EXPECT_THAT(test_vector, Not(ElementsAreArray(kMatcherArray)));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Since ElementsAre() and ElementsAreArray() share much of the
 | 
			
		||||
// implementation, we only do a sanity test for native arrays here.
 | 
			
		||||
TEST(ElementsAreArrayTest, WorksWithNativeArray) {
 | 
			
		||||
  ::std::string a[] = { "hi", "ho" };
 | 
			
		||||
  ::std::string b[] = { "hi", "ho" };
 | 
			
		||||
 | 
			
		||||
  EXPECT_THAT(a, ElementsAreArray(b));
 | 
			
		||||
  EXPECT_THAT(a, ElementsAreArray(b, 2));
 | 
			
		||||
  EXPECT_THAT(a, Not(ElementsAreArray(b, 1)));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests for the MATCHER*() macro family.
 | 
			
		||||
 | 
			
		||||
// Tests that a simple MATCHER() definition works.
 | 
			
		||||
@@ -443,12 +490,23 @@ namespace matcher_test {
 | 
			
		||||
MATCHER(IsOdd, "") { return (arg % 2) != 0; }
 | 
			
		||||
}  // namespace matcher_test
 | 
			
		||||
 | 
			
		||||
TEST(MatcherTest, WorksInNamespace) {
 | 
			
		||||
TEST(MatcherMacroTest, WorksInNamespace) {
 | 
			
		||||
  Matcher<int> m = matcher_test::IsOdd();
 | 
			
		||||
  EXPECT_FALSE(m.Matches(4));
 | 
			
		||||
  EXPECT_TRUE(m.Matches(5));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests that Value() can be used to compose matchers.
 | 
			
		||||
MATCHER(IsPositiveOdd, "") {
 | 
			
		||||
  return Value(arg, matcher_test::IsOdd()) && arg > 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(MatcherMacroTest, CanBeComposedUsingValue) {
 | 
			
		||||
  EXPECT_THAT(3, IsPositiveOdd());
 | 
			
		||||
  EXPECT_THAT(4, Not(IsPositiveOdd()));
 | 
			
		||||
  EXPECT_THAT(-1, Not(IsPositiveOdd()));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests that a simple MATCHER_P() definition works.
 | 
			
		||||
 | 
			
		||||
MATCHER_P(IsGreaterThan32And, n, "") { return arg > 32 && arg > n; }
 | 
			
		||||
@@ -742,14 +800,31 @@ TEST(MatcherPnMacroTest, TypesAreCorrect) {
 | 
			
		||||
      EqualsSumOf(1, 2, 3, 4, 5, 6, 7, 8, 9, '0');
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests that matcher-typed parameters can be used in Value() inside a
 | 
			
		||||
// MATCHER_Pn definition.
 | 
			
		||||
 | 
			
		||||
// Succeeds if arg matches exactly 2 of the 3 matchers.
 | 
			
		||||
MATCHER_P3(TwoOf, m1, m2, m3, "") {
 | 
			
		||||
  const int count = static_cast<int>(Value(arg, m1))
 | 
			
		||||
      + static_cast<int>(Value(arg, m2)) + static_cast<int>(Value(arg, m3));
 | 
			
		||||
  return count == 2;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(MatcherPnMacroTest, CanUseMatcherTypedParameterInValue) {
 | 
			
		||||
  EXPECT_THAT(42, TwoOf(Gt(0), Lt(50), Eq(10)));
 | 
			
		||||
  EXPECT_THAT(0, Not(TwoOf(Gt(-1), Lt(1), Eq(0))));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests Contains().
 | 
			
		||||
 | 
			
		||||
TEST(ContainsTest, ListMatchesWhenElementIsInContainer) {
 | 
			
		||||
  list<int> some_list;
 | 
			
		||||
  some_list.push_back(3);
 | 
			
		||||
  some_list.push_back(1);
 | 
			
		||||
  some_list.push_back(2);
 | 
			
		||||
  EXPECT_THAT(some_list, Contains(1));
 | 
			
		||||
  EXPECT_THAT(some_list, Contains(3.0));
 | 
			
		||||
  EXPECT_THAT(some_list, Contains(2.0f));
 | 
			
		||||
  EXPECT_THAT(some_list, Contains(Gt(2.5)));
 | 
			
		||||
  EXPECT_THAT(some_list, Contains(Eq(2.0f)));
 | 
			
		||||
 | 
			
		||||
  list<string> another_list;
 | 
			
		||||
  another_list.push_back("fee");
 | 
			
		||||
@@ -771,8 +846,8 @@ TEST(ContainsTest, SetMatchesWhenElementIsInContainer) {
 | 
			
		||||
  some_set.insert(3);
 | 
			
		||||
  some_set.insert(1);
 | 
			
		||||
  some_set.insert(2);
 | 
			
		||||
  EXPECT_THAT(some_set, Contains(1.0));
 | 
			
		||||
  EXPECT_THAT(some_set, Contains(3.0f));
 | 
			
		||||
  EXPECT_THAT(some_set, Contains(Eq(1.0)));
 | 
			
		||||
  EXPECT_THAT(some_set, Contains(Eq(3.0f)));
 | 
			
		||||
  EXPECT_THAT(some_set, Contains(2));
 | 
			
		||||
 | 
			
		||||
  set<const char*> another_set;
 | 
			
		||||
@@ -780,7 +855,7 @@ TEST(ContainsTest, SetMatchesWhenElementIsInContainer) {
 | 
			
		||||
  another_set.insert("fie");
 | 
			
		||||
  another_set.insert("foe");
 | 
			
		||||
  another_set.insert("fum");
 | 
			
		||||
  EXPECT_THAT(another_set, Contains(string("fum")));
 | 
			
		||||
  EXPECT_THAT(another_set, Contains(Eq(string("fum"))));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ContainsTest, SetDoesNotMatchWhenElementIsNotInContainer) {
 | 
			
		||||
@@ -795,8 +870,20 @@ TEST(ContainsTest, SetDoesNotMatchWhenElementIsNotInContainer) {
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ContainsTest, DescribesItselfCorrectly) {
 | 
			
		||||
  const int a[2] = { 1, 2 };
 | 
			
		||||
  Matcher<const int(&)[2]> m = Contains(2);
 | 
			
		||||
  EXPECT_EQ("element 1 matches", Explain(m, a));
 | 
			
		||||
 | 
			
		||||
  m = Contains(3);
 | 
			
		||||
  EXPECT_EQ("", Explain(m, a));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ContainsTest, ExplainsMatchResultCorrectly) {
 | 
			
		||||
  Matcher<vector<int> > m = Contains(1);
 | 
			
		||||
  EXPECT_EQ("contains 1", Describe(m));
 | 
			
		||||
  EXPECT_EQ("contains at least one element that is equal to 1", Describe(m));
 | 
			
		||||
 | 
			
		||||
  Matcher<vector<int> > m2 = Not(m);
 | 
			
		||||
  EXPECT_EQ("doesn't contain any element that is equal to 1", Describe(m2));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ContainsTest, MapMatchesWhenElementIsInContainer) {
 | 
			
		||||
@@ -823,7 +910,7 @@ TEST(ContainsTest, MapDoesNotMatchWhenElementIsNotInContainer) {
 | 
			
		||||
 | 
			
		||||
TEST(ContainsTest, ArrayMatchesWhenElementIsInContainer) {
 | 
			
		||||
  const char* string_array[] = { "fee", "fie", "foe", "fum" };
 | 
			
		||||
  EXPECT_THAT(string_array, Contains(string("fum")));
 | 
			
		||||
  EXPECT_THAT(string_array, Contains(Eq(string("fum"))));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ContainsTest, ArrayDoesNotMatchWhenElementIsNotInContainer) {
 | 
			
		||||
@@ -831,4 +918,24 @@ TEST(ContainsTest, ArrayDoesNotMatchWhenElementIsNotInContainer) {
 | 
			
		||||
  EXPECT_THAT(int_array, Not(Contains(5)));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ContainsTest, AcceptsMatcher) {
 | 
			
		||||
  const int a[] = { 1, 2, 3 };
 | 
			
		||||
  EXPECT_THAT(a, Contains(Gt(2)));
 | 
			
		||||
  EXPECT_THAT(a, Not(Contains(Gt(4))));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ContainsTest, WorksForNativeArrayAsTuple) {
 | 
			
		||||
  const int a[] = { 1, 2 };
 | 
			
		||||
  EXPECT_THAT(make_tuple(a, 2), Contains(1));
 | 
			
		||||
  EXPECT_THAT(make_tuple(a, 2), Not(Contains(Gt(3))));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ContainsTest, WorksForTwoDimensionalNativeArray) {
 | 
			
		||||
  int a[][3] = { { 1, 2, 3 }, { 4, 5, 6 } };
 | 
			
		||||
  EXPECT_THAT(a, Contains(ElementsAre(4, 5, 6)));
 | 
			
		||||
  EXPECT_THAT(a, Contains(Contains(5)));
 | 
			
		||||
  EXPECT_THAT(a, Not(Contains(ElementsAre(3, 4, 5))));
 | 
			
		||||
  EXPECT_THAT(a, Contains(Not(Contains(5))));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
}  // namespace
 | 
			
		||||
 
 | 
			
		||||
@@ -53,6 +53,7 @@ namespace internal {
 | 
			
		||||
 | 
			
		||||
namespace {
 | 
			
		||||
 | 
			
		||||
using ::std::tr1::make_tuple;
 | 
			
		||||
using ::std::tr1::tuple;
 | 
			
		||||
 | 
			
		||||
TEST(ConvertIdentifierNameToWordsTest, WorksWhenNameContainsNoWord) {
 | 
			
		||||
@@ -130,6 +131,8 @@ TEST(RemoveConstTest, DoesNotAffectNonConstType) {
 | 
			
		||||
// Tests that RemoveConst removes const from const types.
 | 
			
		||||
TEST(RemoveConstTest, RemovesConst) {
 | 
			
		||||
  CompileAssertTypesEqual<int, RemoveConst<const int>::type>();
 | 
			
		||||
  CompileAssertTypesEqual<char[2], RemoveConst<const char[2]>::type>();
 | 
			
		||||
  CompileAssertTypesEqual<char[2][3], RemoveConst<const char[2][3]>::type>();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests GMOCK_REMOVE_CONST_.
 | 
			
		||||
@@ -721,6 +724,234 @@ TEST(OnCallTest, LogsAnythingArgument) {
 | 
			
		||||
 | 
			
		||||
#endif  // 0
 | 
			
		||||
 | 
			
		||||
// Tests ArrayEq().
 | 
			
		||||
 | 
			
		||||
TEST(ArrayEqTest, WorksForDegeneratedArrays) {
 | 
			
		||||
  EXPECT_TRUE(ArrayEq(5, 5L));
 | 
			
		||||
  EXPECT_FALSE(ArrayEq('a', 0));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ArrayEqTest, WorksForOneDimensionalArrays) {
 | 
			
		||||
  const int a[] = { 0, 1 };
 | 
			
		||||
  long b[] = { 0, 1 };
 | 
			
		||||
  EXPECT_TRUE(ArrayEq(a, b));
 | 
			
		||||
  EXPECT_TRUE(ArrayEq(a, 2, b));
 | 
			
		||||
 | 
			
		||||
  b[0] = 2;
 | 
			
		||||
  EXPECT_FALSE(ArrayEq(a, b));
 | 
			
		||||
  EXPECT_FALSE(ArrayEq(a, 1, b));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ArrayEqTest, WorksForTwoDimensionalArrays) {
 | 
			
		||||
  const char a[][3] = { "hi", "lo" };
 | 
			
		||||
  const char b[][3] = { "hi", "lo" };
 | 
			
		||||
  const char c[][3] = { "hi", "li" };
 | 
			
		||||
 | 
			
		||||
  EXPECT_TRUE(ArrayEq(a, b));
 | 
			
		||||
  EXPECT_TRUE(ArrayEq(a, 2, b));
 | 
			
		||||
 | 
			
		||||
  EXPECT_FALSE(ArrayEq(a, c));
 | 
			
		||||
  EXPECT_FALSE(ArrayEq(a, 2, c));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests ArrayAwareFind().
 | 
			
		||||
 | 
			
		||||
TEST(ArrayAwareFindTest, WorksForOneDimensionalArray) {
 | 
			
		||||
  const char a[] = "hello";
 | 
			
		||||
  EXPECT_EQ(a + 4, ArrayAwareFind(a, a + 5, 'o'));
 | 
			
		||||
  EXPECT_EQ(a + 5, ArrayAwareFind(a, a + 5, 'x'));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ArrayAwareFindTest, WorksForTwoDimensionalArray) {
 | 
			
		||||
  int a[][2] = { { 0, 1 }, { 2, 3 }, { 4, 5 } };
 | 
			
		||||
  const int b[2] = { 2, 3 };
 | 
			
		||||
  EXPECT_EQ(a + 1, ArrayAwareFind(a, a + 3, b));
 | 
			
		||||
 | 
			
		||||
  const int c[2] = { 6, 7 };
 | 
			
		||||
  EXPECT_EQ(a + 3, ArrayAwareFind(a, a + 3, c));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests CopyArray().
 | 
			
		||||
 | 
			
		||||
TEST(CopyArrayTest, WorksForDegeneratedArrays) {
 | 
			
		||||
  int n = 0;
 | 
			
		||||
  CopyArray('a', &n);
 | 
			
		||||
  EXPECT_EQ('a', n);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(CopyArrayTest, WorksForOneDimensionalArrays) {
 | 
			
		||||
  const char a[3] = "hi";
 | 
			
		||||
  int b[3];
 | 
			
		||||
  CopyArray(a, &b);
 | 
			
		||||
  EXPECT_TRUE(ArrayEq(a, b));
 | 
			
		||||
 | 
			
		||||
  int c[3];
 | 
			
		||||
  CopyArray(a, 3, c);
 | 
			
		||||
  EXPECT_TRUE(ArrayEq(a, c));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(CopyArrayTest, WorksForTwoDimensionalArrays) {
 | 
			
		||||
  const int a[2][3] = { { 0, 1, 2 }, { 3, 4, 5 } };
 | 
			
		||||
  int b[2][3];
 | 
			
		||||
  CopyArray(a, &b);
 | 
			
		||||
  EXPECT_TRUE(ArrayEq(a, b));
 | 
			
		||||
 | 
			
		||||
  int c[2][3];
 | 
			
		||||
  CopyArray(a, 2, c);
 | 
			
		||||
  EXPECT_TRUE(ArrayEq(a, c));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests NativeArray.
 | 
			
		||||
 | 
			
		||||
TEST(NativeArrayTest, ConstructorFromArrayReferenceWorks) {
 | 
			
		||||
  const int a[3] = { 0, 1, 2 };
 | 
			
		||||
  NativeArray<int> na(a, kReference);
 | 
			
		||||
  EXPECT_EQ(3, na.size());
 | 
			
		||||
  EXPECT_EQ(a, na.begin());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(NativeArrayTest, ConstructorFromTupleWorks) {
 | 
			
		||||
  int a[3] = { 0, 1, 2 };
 | 
			
		||||
  // Tests with a plain pointer.
 | 
			
		||||
  NativeArray<int> na(make_tuple(a, 3U), kReference);
 | 
			
		||||
  EXPECT_EQ(a, na.begin());
 | 
			
		||||
 | 
			
		||||
  const linked_ptr<char> b(new char);
 | 
			
		||||
  *b = 'a';
 | 
			
		||||
  // Tests with a smart pointer.
 | 
			
		||||
  NativeArray<char> nb(make_tuple(b, 1), kCopy);
 | 
			
		||||
  EXPECT_NE(b.get(), nb.begin());
 | 
			
		||||
  EXPECT_EQ('a', nb.begin()[0]);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(NativeArrayTest, CreatesAndDeletesCopyOfArrayWhenAskedTo) {
 | 
			
		||||
  typedef int Array[2];
 | 
			
		||||
  Array* a = new Array[1];
 | 
			
		||||
  (*a)[0] = 0;
 | 
			
		||||
  (*a)[1] = 1;
 | 
			
		||||
  NativeArray<int> na(*a, kCopy);
 | 
			
		||||
  EXPECT_NE(*a, na.begin());
 | 
			
		||||
  delete[] a;
 | 
			
		||||
  EXPECT_EQ(0, na.begin()[0]);
 | 
			
		||||
  EXPECT_EQ(1, na.begin()[1]);
 | 
			
		||||
 | 
			
		||||
  // We rely on the heap checker to verify that na deletes the copy of
 | 
			
		||||
  // array.
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(NativeArrayTest, TypeMembersAreCorrect) {
 | 
			
		||||
  StaticAssertTypeEq<char, NativeArray<char>::value_type>();
 | 
			
		||||
  StaticAssertTypeEq<int[2], NativeArray<int[2]>::value_type>();
 | 
			
		||||
 | 
			
		||||
  StaticAssertTypeEq<const char*, NativeArray<char>::const_iterator>();
 | 
			
		||||
  StaticAssertTypeEq<const bool(*)[2], NativeArray<bool[2]>::const_iterator>();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(NativeArrayTest, MethodsWork) {
 | 
			
		||||
  const int a[] = { 0, 1, 2 };
 | 
			
		||||
  NativeArray<int> na(a, kCopy);
 | 
			
		||||
  ASSERT_EQ(3, na.size());
 | 
			
		||||
  EXPECT_EQ(3, na.end() - na.begin());
 | 
			
		||||
 | 
			
		||||
  NativeArray<int>::const_iterator it = na.begin();
 | 
			
		||||
  EXPECT_EQ(0, *it);
 | 
			
		||||
  ++it;
 | 
			
		||||
  EXPECT_EQ(1, *it);
 | 
			
		||||
  it++;
 | 
			
		||||
  EXPECT_EQ(2, *it);
 | 
			
		||||
  ++it;
 | 
			
		||||
  EXPECT_EQ(na.end(), it);
 | 
			
		||||
 | 
			
		||||
  EXPECT_THAT(na, Eq(na));
 | 
			
		||||
 | 
			
		||||
  NativeArray<int> na2(a, kReference);
 | 
			
		||||
  EXPECT_THAT(na, Eq(na2));
 | 
			
		||||
 | 
			
		||||
  const int b1[] = { 0, 1, 1 };
 | 
			
		||||
  const int b2[] = { 0, 1, 2, 3 };
 | 
			
		||||
  EXPECT_THAT(na, Not(Eq(NativeArray<int>(b1, kReference))));
 | 
			
		||||
  EXPECT_THAT(na, Not(Eq(NativeArray<int>(b2, kCopy))));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(NativeArrayTest, WorksForTwoDimensionalArray) {
 | 
			
		||||
  const char a[2][3] = { "hi", "lo" };
 | 
			
		||||
  NativeArray<char[3]> na(a, kReference);
 | 
			
		||||
  ASSERT_EQ(2, na.size());
 | 
			
		||||
  EXPECT_EQ(a, na.begin());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests StlContainerView.
 | 
			
		||||
 | 
			
		||||
TEST(StlContainerViewTest, WorksForStlContainer) {
 | 
			
		||||
  StaticAssertTypeEq<std::vector<int>,
 | 
			
		||||
      StlContainerView<std::vector<int> >::type>();
 | 
			
		||||
  StaticAssertTypeEq<const std::vector<double>&,
 | 
			
		||||
      StlContainerView<std::vector<double> >::const_reference>();
 | 
			
		||||
 | 
			
		||||
  typedef std::vector<char> Chars;
 | 
			
		||||
  Chars v1;
 | 
			
		||||
  const Chars& v2(StlContainerView<Chars>::ConstReference(v1));
 | 
			
		||||
  EXPECT_EQ(&v1, &v2);
 | 
			
		||||
 | 
			
		||||
  v1.push_back('a');
 | 
			
		||||
  Chars v3 = StlContainerView<Chars>::Copy(v1);
 | 
			
		||||
  EXPECT_THAT(v3, Eq(v3));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(StlContainerViewTest, WorksForStaticNativeArray) {
 | 
			
		||||
  StaticAssertTypeEq<NativeArray<int>,
 | 
			
		||||
      StlContainerView<int[3]>::type>();
 | 
			
		||||
  StaticAssertTypeEq<NativeArray<double>,
 | 
			
		||||
      StlContainerView<const double[4]>::type>();
 | 
			
		||||
  StaticAssertTypeEq<NativeArray<char[3]>,
 | 
			
		||||
      StlContainerView<const char[2][3]>::type>();
 | 
			
		||||
 | 
			
		||||
  StaticAssertTypeEq<const NativeArray<int>,
 | 
			
		||||
      StlContainerView<int[2]>::const_reference>();
 | 
			
		||||
 | 
			
		||||
  int a1[3] = { 0, 1, 2 };
 | 
			
		||||
  NativeArray<int> a2 = StlContainerView<int[3]>::ConstReference(a1);
 | 
			
		||||
  EXPECT_EQ(3, a2.size());
 | 
			
		||||
  EXPECT_EQ(a1, a2.begin());
 | 
			
		||||
 | 
			
		||||
  const NativeArray<int> a3 = StlContainerView<int[3]>::Copy(a1);
 | 
			
		||||
  ASSERT_EQ(3, a3.size());
 | 
			
		||||
  EXPECT_EQ(0, a3.begin()[0]);
 | 
			
		||||
  EXPECT_EQ(1, a3.begin()[1]);
 | 
			
		||||
  EXPECT_EQ(2, a3.begin()[2]);
 | 
			
		||||
 | 
			
		||||
  // Makes sure a1 and a3 aren't aliases.
 | 
			
		||||
  a1[0] = 3;
 | 
			
		||||
  EXPECT_EQ(0, a3.begin()[0]);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(StlContainerViewTest, WorksForDynamicNativeArray) {
 | 
			
		||||
  StaticAssertTypeEq<NativeArray<int>,
 | 
			
		||||
      StlContainerView<tuple<const int*, size_t> >::type>();
 | 
			
		||||
  StaticAssertTypeEq<NativeArray<double>,
 | 
			
		||||
      StlContainerView<tuple<linked_ptr<double>, int> >::type>();
 | 
			
		||||
 | 
			
		||||
  StaticAssertTypeEq<const NativeArray<int>,
 | 
			
		||||
      StlContainerView<tuple<const int*, int> >::const_reference>();
 | 
			
		||||
 | 
			
		||||
  int a1[3] = { 0, 1, 2 };
 | 
			
		||||
  NativeArray<int> a2 = StlContainerView<tuple<const int*, int> >::
 | 
			
		||||
      ConstReference(make_tuple(a1, 3));
 | 
			
		||||
  EXPECT_EQ(3, a2.size());
 | 
			
		||||
  EXPECT_EQ(a1, a2.begin());
 | 
			
		||||
 | 
			
		||||
  const NativeArray<int> a3 = StlContainerView<tuple<int*, size_t> >::
 | 
			
		||||
      Copy(make_tuple(a1, 3));
 | 
			
		||||
  ASSERT_EQ(3, a3.size());
 | 
			
		||||
  EXPECT_EQ(0, a3.begin()[0]);
 | 
			
		||||
  EXPECT_EQ(1, a3.begin()[1]);
 | 
			
		||||
  EXPECT_EQ(2, a3.begin()[2]);
 | 
			
		||||
 | 
			
		||||
  // Makes sure a1 and a3 aren't aliases.
 | 
			
		||||
  a1[0] = 3;
 | 
			
		||||
  EXPECT_EQ(0, a3.begin()[0]);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
}  // namespace
 | 
			
		||||
}  // namespace internal
 | 
			
		||||
}  // namespace testing
 | 
			
		||||
 
 | 
			
		||||
@@ -60,6 +60,7 @@ bool SkipPrefix(const char* prefix, const char** pstr);
 | 
			
		||||
namespace gmock_matchers_test {
 | 
			
		||||
 | 
			
		||||
using std::stringstream;
 | 
			
		||||
using std::tr1::make_tuple;
 | 
			
		||||
using testing::A;
 | 
			
		||||
using testing::AllOf;
 | 
			
		||||
using testing::An;
 | 
			
		||||
@@ -98,6 +99,7 @@ using testing::StrEq;
 | 
			
		||||
using testing::StrNe;
 | 
			
		||||
using testing::Truly;
 | 
			
		||||
using testing::TypedEq;
 | 
			
		||||
using testing::Value;
 | 
			
		||||
using testing::_;
 | 
			
		||||
using testing::internal::FloatingEqMatcher;
 | 
			
		||||
using testing::internal::FormatMatcherDescriptionSyntaxError;
 | 
			
		||||
@@ -1670,6 +1672,25 @@ TEST(MatchesTest, WorksWithMatcherOnNonRefType) {
 | 
			
		||||
  EXPECT_FALSE(Matches(eq5)(2));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests Value(value, matcher).  Since Value() is a simple wrapper for
 | 
			
		||||
// Matches(), which has been tested already, we don't spend a lot of
 | 
			
		||||
// effort on testing Value().
 | 
			
		||||
TEST(ValueTest, WorksWithPolymorphicMatcher) {
 | 
			
		||||
  EXPECT_TRUE(Value("hi", StartsWith("h")));
 | 
			
		||||
  EXPECT_FALSE(Value(5, Gt(10)));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ValueTest, WorksWithMonomorphicMatcher) {
 | 
			
		||||
  const Matcher<int> is_zero = Eq(0);
 | 
			
		||||
  EXPECT_TRUE(Value(0, is_zero));
 | 
			
		||||
  EXPECT_FALSE(Value('a', is_zero));
 | 
			
		||||
 | 
			
		||||
  int n = 0;
 | 
			
		||||
  const Matcher<const int&> ref_n = Ref(n);
 | 
			
		||||
  EXPECT_TRUE(Value(n, ref_n));
 | 
			
		||||
  EXPECT_FALSE(Value(1, ref_n));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests that ASSERT_THAT() and EXPECT_THAT() work when the value
 | 
			
		||||
// matches the matcher.
 | 
			
		||||
TEST(MatcherAssertionTest, WorksWhenMatcherIsSatisfied) {
 | 
			
		||||
@@ -2765,9 +2786,7 @@ TEST(ByRefTest, AllowsNotCopyableValueInMatchers) {
 | 
			
		||||
// different element types.
 | 
			
		||||
 | 
			
		||||
template <typename T>
 | 
			
		||||
class ContainerEqTest : public testing::Test {
 | 
			
		||||
 public:
 | 
			
		||||
};
 | 
			
		||||
class ContainerEqTest : public testing::Test {};
 | 
			
		||||
 | 
			
		||||
typedef testing::Types<
 | 
			
		||||
    std::set<int>,
 | 
			
		||||
@@ -2901,6 +2920,59 @@ TEST(ContainerEqExtraTest, WorksForMaps) {
 | 
			
		||||
            Explain(m, test_map));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ContainerEqExtraTest, WorksForNativeArray) {
 | 
			
		||||
  int a1[] = { 1, 2, 3 };
 | 
			
		||||
  int a2[] = { 1, 2, 3 };
 | 
			
		||||
  int b[] = { 1, 2, 4 };
 | 
			
		||||
 | 
			
		||||
  EXPECT_THAT(a1, ContainerEq(a2));
 | 
			
		||||
  EXPECT_THAT(a1, Not(ContainerEq(b)));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ContainerEqExtraTest, WorksForTwoDimensionalNativeArray) {
 | 
			
		||||
  const char a1[][3] = { "hi", "lo" };
 | 
			
		||||
  const char a2[][3] = { "hi", "lo" };
 | 
			
		||||
  const char b[][3] = { "lo", "hi" };
 | 
			
		||||
 | 
			
		||||
  // Tests using ContainerEq() in the first dimension.
 | 
			
		||||
  EXPECT_THAT(a1, ContainerEq(a2));
 | 
			
		||||
  EXPECT_THAT(a1, Not(ContainerEq(b)));
 | 
			
		||||
 | 
			
		||||
  // Tests using ContainerEq() in the second dimension.
 | 
			
		||||
  EXPECT_THAT(a1, ElementsAre(ContainerEq(a2[0]), ContainerEq(a2[1])));
 | 
			
		||||
  EXPECT_THAT(a1, ElementsAre(Not(ContainerEq(b[0])), ContainerEq(a2[1])));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ContainerEqExtraTest, WorksForNativeArrayAsTuple) {
 | 
			
		||||
  const int a1[] = { 1, 2, 3 };
 | 
			
		||||
  const int a2[] = { 1, 2, 3 };
 | 
			
		||||
  const int b[] = { 1, 2, 3, 4 };
 | 
			
		||||
 | 
			
		||||
  EXPECT_THAT(make_tuple(a1, 3), ContainerEq(a2));
 | 
			
		||||
  EXPECT_THAT(make_tuple(a1, 3), Not(ContainerEq(b)));
 | 
			
		||||
 | 
			
		||||
  const int c[] = { 1, 3, 2 };
 | 
			
		||||
  EXPECT_THAT(make_tuple(a1, 3), Not(ContainerEq(c)));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(ContainerEqExtraTest, CopiesNativeArrayParameter) {
 | 
			
		||||
  std::string a1[][3] = {
 | 
			
		||||
    { "hi", "hello", "ciao" },
 | 
			
		||||
    { "bye", "see you", "ciao" }
 | 
			
		||||
  };
 | 
			
		||||
 | 
			
		||||
  std::string a2[][3] = {
 | 
			
		||||
    { "hi", "hello", "ciao" },
 | 
			
		||||
    { "bye", "see you", "ciao" }
 | 
			
		||||
  };
 | 
			
		||||
 | 
			
		||||
  const Matcher<const std::string(&)[2][3]> m = ContainerEq(a2);
 | 
			
		||||
  EXPECT_THAT(a1, m);
 | 
			
		||||
 | 
			
		||||
  a2[0][0] = "ha";
 | 
			
		||||
  EXPECT_THAT(a1, m);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests GetParamIndex().
 | 
			
		||||
 | 
			
		||||
TEST(GetParamIndexTest, WorksForEmptyParamList) {
 | 
			
		||||
 
 | 
			
		||||
@@ -154,10 +154,13 @@ using ::std::tr1::tuple;
 | 
			
		||||
using ::std::vector;
 | 
			
		||||
using ::testing::ElementsAre;
 | 
			
		||||
using ::testing::StartsWith;
 | 
			
		||||
using ::testing::internal::NativeArray;
 | 
			
		||||
using ::testing::internal::Strings;
 | 
			
		||||
using ::testing::internal::UniversalTersePrint;
 | 
			
		||||
using ::testing::internal::UniversalPrint;
 | 
			
		||||
using ::testing::internal::UniversalTersePrintTupleFieldsToStrings;
 | 
			
		||||
using ::testing::internal::UniversalPrinter;
 | 
			
		||||
using ::testing::internal::kReference;
 | 
			
		||||
using ::testing::internal::string;
 | 
			
		||||
 | 
			
		||||
#if GTEST_OS_WINDOWS
 | 
			
		||||
@@ -786,6 +789,17 @@ TEST(PrintStlContainerTest, NestedContainer) {
 | 
			
		||||
  EXPECT_EQ("{ { 1, 2 }, { 3, 4, 5 } }", Print(v));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(PrintStlContainerTest, OneDimensionalNativeArray) {
 | 
			
		||||
  const int a[] = { 1, 2, 3 };
 | 
			
		||||
  NativeArray<int> b(a, kReference);
 | 
			
		||||
  EXPECT_EQ("{ 1, 2, 3 }", Print(b));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(PrintStlContainerTest, TwoDimensionalNativeArray) {
 | 
			
		||||
  const int a[][3] = { { 1, 2, 3 }, { 4, 5, 6 } };
 | 
			
		||||
  NativeArray<int[3]> b(a, kReference);
 | 
			
		||||
  EXPECT_EQ("{ { 1, 2, 3 }, { 4, 5, 6 } }", Print(b));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Tests printing tuples.
 | 
			
		||||
 | 
			
		||||
@@ -1013,6 +1027,37 @@ TEST(UniversalTersePrintTest, WorksForCString) {
 | 
			
		||||
  EXPECT_EQ("NULL", ss3.str());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(UniversalPrintTest, WorksForNonReference) {
 | 
			
		||||
  ::std::stringstream ss;
 | 
			
		||||
  UniversalPrint(123, &ss);
 | 
			
		||||
  EXPECT_EQ("123", ss.str());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(UniversalPrintTest, WorksForReference) {
 | 
			
		||||
  const int& n = 123;
 | 
			
		||||
  ::std::stringstream ss;
 | 
			
		||||
  UniversalPrint(n, &ss);
 | 
			
		||||
  EXPECT_EQ("123", ss.str());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(UniversalPrintTest, WorksForCString) {
 | 
			
		||||
  const char* s1 = "abc";
 | 
			
		||||
  ::std::stringstream ss1;
 | 
			
		||||
  UniversalPrint(s1, &ss1);
 | 
			
		||||
  EXPECT_EQ(PrintPointer(s1) + " pointing to \"abc\"", string(ss1.str()));
 | 
			
		||||
 | 
			
		||||
  char* s2 = const_cast<char*>(s1);
 | 
			
		||||
  ::std::stringstream ss2;
 | 
			
		||||
  UniversalPrint(s2, &ss2);
 | 
			
		||||
  EXPECT_EQ(PrintPointer(s2) + " pointing to \"abc\"", string(ss2.str()));
 | 
			
		||||
 | 
			
		||||
  const char* s3 = NULL;
 | 
			
		||||
  ::std::stringstream ss3;
 | 
			
		||||
  UniversalPrint(s3, &ss3);
 | 
			
		||||
  EXPECT_EQ("NULL", ss3.str());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
TEST(UniversalTersePrintTupleFieldsToStringsTest, PrintsEmptyTuple) {
 | 
			
		||||
  EXPECT_THAT(UniversalTersePrintTupleFieldsToStrings(make_tuple()),
 | 
			
		||||
              ElementsAre());
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user