C++ C++;-如何在没有动态浇铸的情况下测试工厂<&燃气轮机;

C++ C++;-如何在没有动态浇铸的情况下测试工厂<&燃气轮机;,c++,c++11,tdd,C++,C++11,Tdd,让我们假设有一个类节点声明如下: class Node{ public: template <typename Functor, typename... Args>> Node(Functor functor, Args...); void process(); private: // placeholder etc. }; 现在的问题是,我无法测试getConfiguredNode方法,因为我不知道存储在引擎盖下的Functor类型 通常情况下,测

让我们假设有一个类节点声明如下:

class Node{
public:
    template <typename Functor, typename... Args>>
    Node(Functor functor, Args...);
    void process();

private:
// placeholder etc.
};
现在的问题是,我无法测试
getConfiguredNode
方法,因为我不知道存储在引擎盖下的
Functor
类型

通常情况下,测试工厂如下所示:

class AbstractClass{
public:
    virtual void doSomething(arguments...) = 0;
};

class Factory{
public:
    AbstractClass& getConfiguredItem(Settings settings)
};

void testCase{

    try{
        dynamic_cast<ExpectedConcreteType&>(factory.getConfiguredItem(settings));
        success();
    }
    catch(...){
         fail()
    }
}
class抽象类{
公众:
虚空doSomething(参数…)=0;
};
阶级工厂{
公众:
AbstractClass和getConfiguredItem(设置)
};
无效测试用例{
试一试{
动态转换(factory.getConfiguredItem(设置));
成功();
}
捕获(…){
失败()
}
}
我想有这样的东西,适合给定的例子

我可以添加
getStoredTypeInfo
方法,但它仅用于测试目的,从工程角度来看这并不好,因此我的问题是:


我如何(如果我可以)正确地测试这样一个工厂的所有工程方面?

根据您向工厂注册类型的方式,一个选项可以是模板化您的工厂类,以便它可以返回“测试”类型而不是“节点”类型

这将保持函子类型注册的一致性,同时允许您仅在测试工具中实例化新的对象类型

Factory<Node> myNodeFactory;
工厂myNodeFactory;
是否:

  • 在测试中封装节点

    Factory<Test> myTestFactory;  // Test object holds an instantiated Node
    
    工厂myTestFactory;//测试对象持有一个实例化的节点
    
  • 返回一对节点并进行测试

    Factory< std::pair<Node,Test> > myTestFactory;
    
    FactorymyTestFactory;
    
  • 从两个工厂实例构造节点和测试

    Factory<Node> myNodeFactory;
    Factory<Test> myTestFactory;  // Test receives a Node instance to test
    
    工厂myNodeFactory;
    工厂myTestFactory;//Test接收要测试的节点实例
    

根据向工厂注册类型的方式,一个选项可以是模板化工厂类,以便它可以返回“测试”类型而不是“节点”类型

这将保持函子类型注册的一致性,同时允许您仅在测试工具中实例化新的对象类型

Factory<Node> myNodeFactory;
工厂myNodeFactory;
是否:

  • 在测试中封装节点

    Factory<Test> myTestFactory;  // Test object holds an instantiated Node
    
    工厂myTestFactory;//测试对象持有一个实例化的节点
    
  • 返回一对节点并进行测试

    Factory< std::pair<Node,Test> > myTestFactory;
    
    FactorymyTestFactory;
    
  • 从两个工厂实例构造节点和测试

    Factory<Node> myNodeFactory;
    Factory<Test> myTestFactory;  // Test receives a Node instance to test
    
    工厂myNodeFactory;
    工厂myTestFactory;//Test接收要测试的节点实例
    

您可以使用
过程
行为间接测试。是的,我可以这样做,但这也是一种糟糕的做法,因为我想直接测试工厂的行为,而不是通过直接测试节点的行为间接测试工厂。此外,函子本身是在不同的单元测试中测试的,所以我的测试随时都会失败,该函子的测试也会失败。您可以使用
进程
行为进行间接测试。是的,我可以这样做,但这同样是一种糟糕的做法,因为我想直接测试工厂的行为,而不是通过直接测试节点的行为间接测试工厂。此外,函子本身在不同的单元测试中进行测试,因此我的测试随时都会失败,该函子的测试也会失败。嗯,现在我仔细阅读了您的问题,您似乎想测试工厂本身,而不是结果节点的行为。如果不适用于您的情况,我将删除此答案。也许您可以详细解释一下需要测试的行为。工厂在构建
节点时如何选择
Functor
?似乎这种抽象是您的
动态\u cast
模式无法使用的原因。工厂总是创建
节点
,所以这不是问题。真正要测试的是工厂选择
Functor
。您是否可以调整我的建议,将工厂模板化,以便构建的工厂
测试
可以执行构建时间类型检查并设置通过/失败状态(可能是验证参数),例如
工厂
?你们的工厂是一次性的,但这对你们的目的来说已经足够了。我想我不太理解你们的建议。你的意思是让我的工厂成为模板?即使我的生产代码中不需要它?如果是这样,我想我更愿意,那个节点可以返回存储的Functor的
typeid()
,并对其进行比较。但这两种解决方案都会影响我的生产代码以进行测试。通过使用工厂总是创建相同类型的模式,您已经解决了这个问题。似乎在工厂内部本质上存在另一个工厂,它确定
Functor
和参数。也许您可以将该逻辑抽象为一些可单元测试的东西,这样
工厂
本身就可以包装该行为。那么就更容易争辩说,生产代码并没有受到测试的驱动。。。尽管这会影响生产代码的布局,但并不完全如此。在工厂中,有三种类型可以返回,这三种类型是具有不同参数编号和类型的3个函子。为了使它成为一种类型,我将它们绑定到参数,这或多或少就是我获取节点的方式。嗯,现在我更仔细地阅读了您的问题,您似乎想测试工厂本身,而不是结果节点的行为。如果不适用于您的情况,我将删除此答案。也许您可以详细解释一下需要测试的行为。工厂在构建
节点时如何选择
Functor
?似乎这种抽象是您的
动态\u cast
模式无法使用的原因。工厂总是创建
节点
,所以这不是问题。真正要测试的是工厂选择
Functor
。你能适应我的建议吗