C++ Gmock - 匹配结构

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/23938233/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-28 00:35:28  来源:igfitidea点击:

Gmock - matching structures

c++gmock

提问by NiladriBose

How can I match value of an element in a union for an input argument e.g - if I mock a method with the following signatiure -

如何将联合中元素的值与输入参数匹配,例如 - 如果我模拟具有以下签名的方法 -

    struct SomeStruct
    {   
        int data1;
        int data2; 
    };

    void SomeMethod(SomeStruct data);

How can I match that mock for this method was called with correct value in argument?

我怎样才能匹配这个方法的模拟是用参数中的正确值调用的?

回答by NiladriBose

After reading through the Google mock documentation in detail, I solved my problem as documented in Defining Matcherssection. (An example would have been great!)

详细阅读 Google 模拟文档后,我解决了定义匹配器部分中记录的问题。(一个例子会很棒!)

So the solution is to use the MATCHER_Pmacros to define a custom matcher. So for the matching SomeStruct.data1I defined a matcher:

所以解决方案是使用MATCHER_P宏来定义自定义匹配器。所以对于匹配SomeStruct.data1我定义了一个匹配器:

MATCHER_P(data1AreEqual, ,"") { return (arg.data1 == SomeStructToCompare.data1); }

to match it in an expectation I used this custom macro like this:

为了符合预期,我使用了这个自定义宏,如下所示:

EXPECT_CALL(someMock, SomeMethod(data1AreEqual(expectedSomeStruct)));

Here, expectedSomeStructis the value of the structure.data1we are expecting.

这里,expectedSomeStructstructure.data1我们期望的值。

Note that, as suggested in other answers (in this post and others), it requires the unit under test to change to make it testable. That should not be necessary! E.g. overloading.

请注意,正如其他答案(在这篇文章和其他文章中)所建议的,它需要更改被测单元以使其可测试。那应该没有必要!例如超载。

回答by JukkaA

If there a need to explicitly test for specific value of just one field of a struct (or one "property" of a class), gmock has a simple way to test this with the "Field" and "Property" definitions. With a struct:

如果需要显式测试结构的一个字段(或类的一个“属性”)的特定值,gmock 有一种简单的方法可以使用“字段”和“属性”定义进行测试。使用结构:

EXPECT_CALL( someMock, SomeMethod( Field( &SomeStruct::data1, expectedValue )));

Or, alternatively if we have SomeClass (intead of SomeStruct), that has private member variables and public getter functions:

或者,如果我们有 SomeClass(而不是 SomeStruct),它有私有成员变量和公共 getter 函数:

EXPECT_CALL( someMock, SomeMethod( Property( &SomeClass::getData1, expectedValue )));

回答by Lilshieste

Google provides some good documentation on using gmock, full of example code. I highly recommend checking it out:

谷歌提供了一些关于使用 gmock 的很好的文档,里面有很多示例代码。我强烈建议检查一下:

https://github.com/google/googletest/blob/master/googlemock/docs/cook_book.md#using-matchers

https://github.com/google/googletest/blob/master/googlemock/docs/cook_book.md#using-matchers

As you pointed out, a default equality operator (==) isn't automatically created for class types (including PODs). Since this operator is used by gmock when matching parameters, you would need to explicitly define it in order to use the type as you would any other type (as seen below):

正如您所指出的,==不会为类类型(包括 POD)自动创建默认的相等运算符 ( )。由于 gmock 在匹配参数时使用此运算符,因此您需要显式定义它,以便像使用任何其他类型一样使用该类型(如下所示):

    // Assumes `SomeMethod` is mocked in `MockedObject`
    MockedObject foo;
    SomeStruct expectedValue { 1, 2 };

    EXPECT_CALL(foo, SomeMethod(expectedValue));

So, the most straightforward way of dealing with this is to define an equality operator for the struct:

因此,处理这个问题最直接的方法是为结构定义一个相等运算符:

struct SomeStruct
{   
    int data1;
    int data2; 

    bool operator==(const SomeStruct& rhs) const
    {
        return data1 == rhs.data1
            && data2 == rhs.data2;
    }
};

If you don't want to go that route, you can consider using the Field matcherto match the parameter based on the values of its member variables. (If a test is interested in comparing equality between instances of the struct, though, it's a good indication that other code will be interested as well. So it'd likely be worthwhile to just define an operator==and be done with it.)

如果你不想走那条路,你可以考虑使用字段匹配器根据其成员变量的值来匹配参数。(但是,如果测试对比较结构实例之间的相等性感兴趣,那么这很好地表明其他代码也会感兴趣。因此,定义 anoperator==并完成它可能是值得的。)

回答by Jordan

This is basically answered above but I want to give you one more good example:

这基本上已经在上面回答了,但我想再给你一个很好的例子:

// some test type
struct Foo {
    bool b;
    int i;
};

// define a matcher if ==operator is not needed in production
MATCHER_P(EqFoo, other, "Equality matcher for type Foo") {
    return std::tie(arg.b, arg.i) == std::tie(other.b, other.i);
}

// example usage in your test
const Foo test_value {true, 42};
EXPECT_CALL(your_mock, YourMethod(EqFoo(test_value)));

回答by BWD

Maybe useless as the question has been answered long time ago but here is a solution that works with any structure and which does not use MATCHER or FIELD.

也许没用,因为这个问题很久以前就已经回答过了,但这里有一个适用于任何结构并且不使用 MATCHER 或 FIELD 的解决方案。

Suppose we are checking: methodName(const Foo& foo):

假设我们正在检查:methodName(const Foo& foo):

using ::testing::_;

struct Foo {
    ...
    ...
};

EXPECT_CALL(mockObject, methodName(_))
    .WillOnce([&expectedFoo](const Foo& foo) {
        // Here, gtest macros can be used to test struct Foo's members
        // one by one for example (ASSERT_TRUE, ASSERT_EQ, ...)
        ASSERT_EQ(foo.arg1, expectedFoo.arg1);
    });