假设我有一个基类MySet
:
class MySet {
std::vector<int> set;
public:
bool disjoint(const MySet &other) const {
// loop over entire set and see if any elements
// are in other.set
}
};
我有一个派生类SortedRange
:
class SortedRange : public MySet {
// All integers between two limits
public:
using MySet::disjoint;
bool disjoint(const SortedRange &other) const {
return set.first() > other.set.last()
|| other.set.first() > set.last();
}
};
disjoint
中的MySet
方法适用于从MySet
派生的每个类,但是当找到两个SortedRanges
之间的不相交时,重载disjoint
是有意义的1}}派生类中的方法:
int main() {
MySet* base = new Set();
SortedRange* derived = new SortedRange();
derived->disjoint(*derived); // Can use optimized disjoint function
derived->disjoint(*base); // Should fall back on base disjoint function
}
我已经读到name hiding是有充分理由加入的,以这种方式颠覆它是不好的做法。
有没有更好的方法来实现这样的事情而不会破坏名称隐藏?
答案 0 :(得分:1)
引入名称隐藏的原因是为了处理我们的情况:
class Base {
// stuff
};
class Derived : public Base {
// more stuff
public:
static int foo(int);
};
并且调用Derived::foo()
并以文字'a'
作为参数。然后,Base
的开发人员添加了一个新的私有函数Base::foo(char)
。没有名称隐藏,程序突然停止编译 - 对Derived::foo
的调用解析为Base
中的私有成员。名称隐藏阻止了这一点
以上不是您示例中的问题(因为using
表示您已经知道foo
/ disjoint
),因此重载基类成员函数本质上并不坏。
然而,你的激励例子不是很激励 - SortedRange
感觉不像是MySet
。我怀疑继承是正确的方法。 (除非SortedRange
应该代表两个限制之间的所有整数,否则disjoint
实现不正确 - 它将返回[1, 3, 5]
,而不是与{[2, 4, 6]
不相交1}})