我有一个类,它包含一些基于某些配置的(持久)摄像头。各种类与集合相关联,并且集合提供了与实际实现的各种接口。每个摄像机用户都以自己的方式与集合相关联(人们几乎可以认为它与自己的集合相关联,但实现可能会巩固所有责任,例如:
#include <memory>
#include <map>
enum eCameraType{ eCameraType_IR, eCameraType_HDTV };
template <class CameraIF>
struct CameraCollectionIF
{
virtual CameraIF& camera( eCameraType, typename CameraIF::Tag = typename CameraIF::Tag() ) = 0;
protected:
~CameraCollectionIF(){}
};
struct CameraControlIF_A
{
struct Tag{};
virtual void doX() = 0;
};
struct CameraControllerA
{
void foo()
{
//Gets the camera in terms of responsibility associated with
// applicable control IF, but other classes can get camera (control) in
// terms of their responsibility, and that without ambiguity...
collection_->camera( eCameraType_HDTV ).doX();
}
std::shared_ptr<CameraCollectionIF<CameraControlIF_A>> collection_;
};
struct CameraControlIF_B
{
struct Tag{};
virtual void doY() = 0;
};
struct CameraControllerB
{
void foo()
{
//Gets the camera in terms of responsibility associated with
// applicable control IF, but other classes can get camera (control) in
// terms of their responsibility, and that without ambiguity...
collection_->camera( eCameraType_IR ).doY();
}
std::shared_ptr<CameraCollectionIF<CameraControlIF_B>> collection_;
};
//Now implementation of actual collection...
struct Camera : CameraControlIF_A, CameraControlIF_B
{
//etc...
};
struct CameraCollectionForConfigurtionX :
CameraCollectionIF<CameraControlIF_A>,
CameraCollectionIF<CameraControlIF_B>
{
private:
//Assume for now all camera types shall exist in map, therefore lookup can't
// fail...
virtual CameraControlIF_A& camera(
eCameraType cameraID, CameraControlIF_A::Tag ) override
{
return( *cameras_[cameraID] );
}
virtual CameraControlIF_B& camera(
eCameraType cameraID, CameraControlIF_B::Tag ) override
{
return( *cameras_[cameraID] );
}
//etc...
std::map<eCameraType, std::unique_ptr<Camera>> cameras_;
};
// Other configurations may exist that hold different collection of cameras....
可以说上面提到的基本原理,但它确实提供了各种控制器和它们的摄像机之间的分离,而与系统的配置无关。
我的问题是:
由于虚拟函数“camera”从未通过集合的公共接口调用,我认为没有必要指定默认参数与base的相同,实际上,可以省略它完全是:
virtual CameraIF& camera(
eCameraType, typename CameraIF::Tag = typename CameraIF::Tag() ) = 0;
VS
virtual CameraControlIF_A& camera(
eCameraType cameraID, CameraControlIF_A::Tag );
添加到有关默认参数的问题,是上面提到的防止模糊重载(在实现中)常见的技术吗?
答案 0 :(得分:1)
当重写使用基类中的默认参数声明的virtual
函数时,可以添加另一个默认参数, 甚至可以具有不同的值!但是,在覆盖函数中指定默认参数是一个非常糟糕的主意,因此使用不同的值。在任何情况下,您都不需要指定默认值,但 do 需要采用相应的参数,否则它不是重写函数:作为覆盖的函数必须匹配完全基类声明(除非返回类型是指针或引用,否则它可以是协变的)。在C ++中(自2011年修订版以来),您还可以使用override
[contextual]关键字跟随覆盖声明,以使编译器验证声明确实是覆盖。