确保派生类构造函数必须调用特定的基类方法 [英] Ensure derived class constructor must call specific base class method
问题描述
在C ++(03)类中,我有一个成员变量,在对象构造过程中必须为该变量赋一个值.但是,只有派生类可以计算所需的值.如本博文所述确实C ++要求您从其派生类中初始化基类成员吗?,我知道派生类不能初始化基类成员,但是分配对我来说已经足够.
In a C++(03) class, I have a member variable, which must be assigned a value during object construction. However, only the derived class can compute the required value. As discussed in this post Does C++ require you to initialize base class members from its derived class?, I understand that the derived class cannot initialize a base class member, but an assignment is sufficient for me.
因此,我在基类中提供了一种分配值的方法,但是我无法弄清楚如何强制派生类对其进行调用.下面的示例代码说明了这一点.
Hence, I provide a method in the base class to assign a value, but I cannot figure out how I can force the derived class to call it. The below sample code illustrates this point.
class Base {
public:
Base() {}
setFoo(unsigned inFoo) { foo = inFoo; }
private:
unsigned foo;
};
class Derived : public Base {
Derived() : Base() {
unsigned desired = ... // do calculations to get the desired value
setFoo(desired); // --> how to ensure that derived class calls this?
}
};
foo
然后由其他几种基类方法使用.即使我在setFoo()
中设置了标志",也没有可以检查它的后构造器"方法.基类中还有其他使用foo
的方法.我可以在那里检查它,但是这样做太乏味,容易出错并且效率低下.
The foo
is then used by several other Base class methods. Even if I set a "flag" in the setFoo()
, there's no "post-constructor" method where I can check it. There are several other methods in the base class where foo
is used. I could check it there, but it is too tedious, error-prone and inefficient to do so.
我很抱歉,如果以前有人问过这个问题.在通过询问确保派生类构造函数必须调用特定的基类方法"和强制派生类分配基类成员"进行询问之前,我确实尝试在此处找到它.我遇到了一些有用的帖子强制派生类使用基类的构造函数,但不幸的是,它们没有解决我的问题.
My apologies if this has been asked before. I did try to find it here before asking by searching for "Ensure derived class constructor must call specific base class method" and "Force derived class to assign base class member". I came across some useful posts How can I initialize a const variable of a base class in a derived class' constructor in C++? and Force a Derived Class to use the Constructor of the Base Class , but they unfortunately do not address my question.
您能否建议我采用一种合适的方法来解决这种情况?需要一种编译时检查解决方案,但如果不可能,则运行时检查也将有所帮助.尽管我不能使用C ++ 11解决我的问题,但我也很高兴学习任何C ++ 11解决方案.感谢您的考虑.
Could you please suggest me a suitable approach to address this situation? A compile-time checking solution would be desirable, but if that is not possible, a runtime check would also help. Although I cannot use C++11 for my problem, I would be glad to learn any C++11 solutions as well. Thanks for your consideration.
编辑当然,也可以将其记录为一个要求,但是我想了解是否有程序化的解决方案.
Edit Of course, documenting this as a requirement is also an option, but I would like to learn if there's a programmatic solution.
Edit2 我同意答案,即应该在构造函数参数中传递该值,如果我必须从头开始编写Base
,那么我就不会要求这种方法了.问题是,由于遗留原因,Base
已经具有多个构造函数参数(9),并且我希望通过将它们卸载"到构造函数主体来避免添加更多的(3).从长远来看,必须对代码进行重构.
Edit2 I agree with the answers saying that the value should be passed in constructor parameter, and if I had to write Base
from scratch, I wouldn't have asked for this approach. The problem is that due to legacy reasons, Base
already has several constructor parameters (9), and I was hoping to avoid adding more (3) by "offloading" them to the constructor body. In the long term though, the code has to be refactored.
Edit3 很抱歉,进行了如此多的修改.我可以随意修改Base
类,但是Derived
类在客户端代码中,我无法控制.
Edit3 Sorry for so many edits. I can modify the Base
class as I please, but the Derived
class is in client code, which I cannot control.
推荐答案
如果派生类构造函数必须调用setFoo()
,那么我认为这是一个设计问题.最好设计基类,以使其构造函数将所需值作为参数,并让派生类将计算值传递为:
If the derived class constructor must call setFoo()
, then I think that is a design problem. It is better to design the base class, such that it's constructor takes the desired value as argument, and let the derived class pass the computed value as:
class Base {
public:
Base(unsigned int foo) : m_foo (foo) {} //define this constructor
private:
unsigned int m_foo; //member data
};
class Derived : public Base {
Derived() : Base(computeValue())
{
}
private:
static unsigned int computeValue() //it may take argument(s)
{
unsigned int desired = ... //do calculations to get the desired value
return desired;
}
};
这篇关于确保派生类构造函数必须调用特定的基类方法的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!