C++ c++;设计:减少深层类层次结构中的耦合 请考虑该类层次结构: #include <iostream> struct Base { Base(int arg1, int arg2, int arg3, int arg4) { std::cout << "Base::Base:" << arg1 << "," << arg2 << "," << arg3 << "," << arg4 << std::endl; } void BaseDoWork() { std::cout << "Base::BaseDoWork" << std::endl; } }; struct Derived1:public Base { Derived1(int arg1, int arg2, int arg3, int arg4):Base(arg1, arg2, arg3, arg4){} void DerivedDoWork() { BaseDoWork(); } }; struct Derived2:public Derived1 { Derived2(int arg1, int arg2, int arg3, int arg4):Derived1(arg1, arg2, arg3, arg4){} }; int main(int argc, char *argv[]) { Derived2 myDerived2(1,2,3,4); myDerived2.DerivedDoWork(); return 0; } #包括 结构基 { 基数(整数arg1、整数arg2、整数arg3、整数arg4) { std::cout
假设这是真正的层次结构,如果C++ c++;设计:减少深层类层次结构中的耦合 请考虑该类层次结构: #include <iostream> struct Base { Base(int arg1, int arg2, int arg3, int arg4) { std::cout << "Base::Base:" << arg1 << "," << arg2 << "," << arg3 << "," << arg4 << std::endl; } void BaseDoWork() { std::cout << "Base::BaseDoWork" << std::endl; } }; struct Derived1:public Base { Derived1(int arg1, int arg2, int arg3, int arg4):Base(arg1, arg2, arg3, arg4){} void DerivedDoWork() { BaseDoWork(); } }; struct Derived2:public Derived1 { Derived2(int arg1, int arg2, int arg3, int arg4):Derived1(arg1, arg2, arg3, arg4){} }; int main(int argc, char *argv[]) { Derived2 myDerived2(1,2,3,4); myDerived2.DerivedDoWork(); return 0; } #包括 结构基 { 基数(整数arg1、整数arg2、整数arg3、整数arg4) { std::cout,c++,coupling,C++,Coupling,假设这是真正的层次结构,如果Derived1是Base派生类,则必须知道如何构造父类(Base) 据我所知,也许我错了,如果Derived1不是一个真正的Base派生(子)类,只需要知道它的接口,就不需要知道如何构造Base实例。所以您可以按如下方式定义Derived1: struct Derived1 { Derived1(int arg1, int arg2, int arg3, int arg4) {} ..... }; struct Base {
Derived1
是Base
派生类,则必须知道如何构造父类(Base
)
据我所知,也许我错了,如果Derived1
不是一个真正的Base
派生(子)类,只需要知道它的接口,就不需要知道如何构造Base
实例。所以您可以按如下方式定义Derived1:
struct Derived1
{
Derived1(int arg1, int arg2, int arg3, int arg4)
{}
.....
};
struct Base
{
Base(int arg1, int arg2, int arg3, int arg4)
{
std::cout << "Base::Base:" << arg1 << "," << arg2 << "," << arg3 << "," << arg4 << std::endl;
}
virtual void BaseDoWork()
{
std::cout << "Base::BaseDoWork" << std::endl;
}
};
struct Derived1
{
Derived1(int arg1, int arg2, int arg3, int arg4)
{}
template <typename T>
void DerivedDoWork(T & base) // only knows T interface
{
base.BaseDoWork();
}
};
struct Derived2 : public Base, public Derived1
{
Derived2(int arg1, int arg2, int arg3, int arg4) :
Base(arg1, arg2, arg3, arg4),
Derived1(arg1, arg2, arg3, arg4)
{}
virtual void DerivedDoWork()
{
Derived1::DerivedDoWork<Base>(*(static_cast<Base *>(this)));
}
};
只有Base
派生类需要知道如何构造Base
:
struct Derived2 : public Base
{
Derived2(int arg1, int arg2, int arg3, int arg4) :
Base(arg1, arg2, arg3, arg4)
{}
.....
};
现在,如果Derived2
确实是Derived1
子级,则必须知道如何创建它的父级。以前的代码是:
struct Derived2 : public Base, public Derived1
{
Derived2(int arg1, int arg2, int arg3, int arg4) :
Base(arg1, arg2, arg3, arg4),
Derived1(arg1, arg2, arg3, arg4)
{}
.....
};
如果必须使用Derived1
中的Base::basedWork()
方法,则可以如下定义类:
struct Derived1
{
Derived1(int arg1, int arg2, int arg3, int arg4)
{}
.....
};
struct Base
{
Base(int arg1, int arg2, int arg3, int arg4)
{
std::cout << "Base::Base:" << arg1 << "," << arg2 << "," << arg3 << "," << arg4 << std::endl;
}
virtual void BaseDoWork()
{
std::cout << "Base::BaseDoWork" << std::endl;
}
};
struct Derived1
{
Derived1(int arg1, int arg2, int arg3, int arg4)
{}
template <typename T>
void DerivedDoWork(T & base) // only knows T interface
{
base.BaseDoWork();
}
};
struct Derived2 : public Base, public Derived1
{
Derived2(int arg1, int arg2, int arg3, int arg4) :
Base(arg1, arg2, arg3, arg4),
Derived1(arg1, arg2, arg3, arg4)
{}
virtual void DerivedDoWork()
{
Derived1::DerivedDoWork<Base>(*(static_cast<Base *>(this)));
}
};
struct Base
{
基数(整数arg1、整数arg2、整数arg3、整数arg4)
{
std::cout当您将从Base
继承Derived1
公开时,结果是Derived1
已经知道如何构造Base
,因此如果您想Derived1
不知道如何构造Base
,也许最好不要从Base
继承它,将Base
作为某种表演者分开
考虑这段代码,我并不认为这是解决方案,但它可能会让您产生其他想法(类的名称相同):
#包括
结构基
{
Base()
{
是的,这可能是最简单的解决方案。我从Derived1构造函数中删除了参数列表,因为将Derived1从该参数列表中解耦是主要目标之一。而DoWork()方法不需要是虚拟的。我没有想到将实际对象存储在Derived1中。据我所知,您为Base添加的默认构造函数从未被调用:我是否缺少此用途?@SimonElliott,Base
的默认构造函数在创建Derived1
对象时被调用一次,我只是添加了默认c构造函数将Base
对象作为Derived1
的成员。您可以使用T&object
,const T&object
或T*object
,const T*object
替换T object
,并在Derived1
构造函数中初始化此引用/指针,这样Base
就不会是成员对于Derived1
,这是有道理的。我没有单独测试实例化Derived1。