英文:
Double inheritance type deduction
问题
我有以下的模板类:
template<class T>
class Foo {
public:
void Bar(T* t) { member = t; }
private:
T* member;
};
这被用作另一个类的基类(两次):
class AwesomeClass : public Foo<ISomeInterface>, public Foo<IOtherInterface> {};
然后像这样调用:
class Caller {
void Init(ISomeInterface * i) {
AwesomeClass a;
a.Bar(i);
}
}
然而,这不会编译通过,它会声明调用Bar是不明确的。因此,我需要使用a.Foo<ISomeInterface>::Bar(i)
,因为显然编译器无法确定要调用哪个Bar(即使给定了一个ISomeInterface对象)。是否有解决这个问题的方法?
此外,我想知道继承是否是这里的“正确”方法,或者组合是否更好的选择。
英文:
I have the following template class:
template<class T>
class Foo {
public:
void Bar(T* t) { member = t; }
private:
T* member;
};
This is used (twice) as a base class for a different class:
class AwesomeClass : public Foo<ISomeInterface>, public Foo<IOtherInterface> {};
Which is then called something like this:
class Caller {
void Init(ISomeInterface * i) {
AwesomeClass a;
a.Bar(i);
}
}
However this does not compile, stating that the call to Bar is ambiguous. Therefore I need to use a.Foo<ISomeInterface>::Bar(i)
, because apparently the compiler cannot determine which Bar to call (even thought it is given an ISomeInterface object). Any ways around this?
Also I am wondering if inheritance is the 'correct' approach here or if composition would be a better option.
答案1
得分: 4
你可以将 Bar
引入到 AwesomeClass
中,然后两者都可以在 AwesomeClass
的范围内找到,然后会触发重载解析。例如:
class AwesomeClass : public Foo<ISomeInterface>, public Foo<IOtherInterface> {
public:
using Foo<ISomeInterface>::Bar;
using Foo<IOtherInterface>::Bar;
};
英文:
You can introduce Bar
s into AwesomeClass
, then both can be found in scope of AwesomeClass
then overload resolution kicks in. E.g.
class AwesomeClass : public Foo<ISomeInterface>, public Foo<IOtherInterface> {
public:
using Foo<ISomeInterface>::Bar;
using Foo<IOtherInterface>::Bar;
};
答案2
得分: 1
你想要友元函数和ADL。这样,你就不需要逐个从每个基类中using
每个这样的方法。
template <typename T>
class Foo
{
T *member = nullptr;
public:
friend void Bar(Foo &self, T *t)
{
self.member = t;
}
};
void Init(ISomeInterface *i)
{
AwesomeClass a;
Bar(a, i);
}
英文:
You want friend functions and ADL. This way you don't need to individually using
every such method from every base.
template <typename T>
class Foo
{
T *member = nullptr;
public:
friend void Bar(Foo &self, T *t)
{
self.member = t;
}
};
void Init(ISomeInterface * i)
{
AwesomeClass a;
Bar(a, i);
}
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论