我有2个方法的课
class A
{
void Fun()
{
if(FunRet()>0){///} else {///}
}
int FunRet()
{ return 4;}
};
我想测试Fun()方法取决于FunRet返回的内容。所以我想模仿FunRet。 我宁愿不要把FunRet变成虚拟的。我怎么能这样做?
答案 0 :(得分:3)
您可以注入类内依赖项。在这种情况下,make fun接受一个值而不是计算它:
class A
{
void Fun(int x)
{
if(x>0){///} else {///}
}
int FunRet()
{ return 4;}
};
然后你的测试可以将任意值传递给Fun()。如果您需要强制正确使用,请编写公开版本以在API中公开,并使用私有版本进行测试:
class A {
public:
void Fun() { return Fun(FunRet()); }
private:
void Fun(int x); // for testing.
};
答案 1 :(得分:1)
您可以将Fun方法提取到实现接口的计算器类中。您应该在构造函数中将该接口的实例传递给A类。
在测试中,您可以使用其他实现该接口的类来返回其他值。
此方法还有一个很大的优势,即您可以分离计算值和使用计算值的问题。
class A {
public:
A (IFunCalc calc) { m_calc = calc; }
void Fun { if calc.FunRet() > 4 ... }
private:
IFunCalc m_calc;
}
class FunCalc : IFunCulc {
public:
int FunRet { return 4; }
}
class FunCalc4Test : IFunCalc {
public:
int FunRet { return 27; }
}
答案 2 :(得分:0)
我认为你错过了这个指针。
... if ( this->FunRet() > 0 ) { ...
答案 3 :(得分:0)
如果您使用依赖项注入并模拟测试对象,则可以使用模拟对象而无需使用虚函数。
class AParameters
{
public:
int FunRet()
{ return 4;}
};
class MockAParameters
{
public:
MOCK_METHOD0(FunRet, int());
};
template<class Parameters>
class AImpl
{
public:
AImpl(Parameters& parameters):parameters(parameters){}
void Fun()
{
if(parameters.FunRet()>0){///} else {///}
}
private:
Parameters& parameters;
};
typedef AImpl<AParameters> A;
typedef AImpl<MockAParameters> ATestObject;
void Test::funUsesFunRet()
{
MockAParameters params;
EXPECT_CALL(params, FunRet());
ATestObject object(params);
object.Fun();
}
答案 4 :(得分:0)
我相信FunRet
是Fun
的内部实施细节。因此,Fun
不需要与FunRet
隔离进行测试。只需测试Fun
,不要担心它调用FunRet
。