【发布时间】:2017-12-12 10:17:48
【问题描述】:
我需要调用派生自基类的init(int* iNumber) 函数。
BaseClass.h
#pragma once
#include "stdafx.h"
template <class T>
class BaseClass
{
public:
BaseClass() {}
virtual ~BaseClass() {}
virtual void init(T* object) = 0;
};
ChildClass.h
#pragma once
#include "BaseClass.h"
class ChildClass : public BaseClass<int>, public BaseClass<float>
{
public:
ChildClass() {}
virtual ~ChildClass() {}
};
ChildClassImpl.h
#pragma once
#include "ChildClass.h"
class ChildClassImpl : public ChildClass
{
public:
ChildClassImpl();
virtual ~ChildClassImpl();
private:
void init(int* iNumber) override;
void init(float* fNumber) override;
};
ChildClassImpl.cpp
#include "stdafx.h"
#include <iostream>
#include "ChildClassImpl.h"
ChildClassImpl::ChildClassImpl(){}
ChildClassImpl::~ChildClassImpl(){}
void ChildClassImpl::init(int* iNumber)
{
std::cout << "Integer constructor: " << *iNumber << std::endl;
}
void ChildClassImpl::init(float* fNumber)
{
std::cout << "Float constructor: " << *fNumber << std::endl;
}
主类
#include "stdafx.h"
#include <iostream>
#include "ChildClassImpl.h"
using namespace std;
int main()
{
ChildClass* childClass = new ChildClassImpl();
int x = 10;
childClass->init(&x);
cout << "Test" << endl;
getchar();
return 0;
}
在编译时会报错
Severity Code Description Project File Line Error (active) "BaseClass<T>::init [with T=int]" is ambiguous ConsoleApplication4 d:\Learning\ConsoleApplication4\ConsoleApplication4\ConsoleApplication4.cpp 14
我在这里做错了什么?我怎样才能通过最小的更改来修复它?
【问题讨论】:
-
将
using BaseClass<int>::init;using BaseClass<float>::init;放在ChildClass的声明中 -
您从
ChildClassImpl::init函数编写的输出告诉我您不应该拥有这些函数。相反,它们的功能应该放在 actual 构造函数中。 -
@SPD:公平地说,这是一个说明问题的小例子,而不是一个好的程序设计的广告。
-
谢谢@PiotrSkotnicki。它确实奏效了。如果您能解释为什么会发生这种情况,那就更好了。为什么编译器无法找出正确的基类?
-
预模板 C++ 的解析规则基本上说基础方法仅在名称上自动提升/冲突,并且不考虑参数,这是一个弱点。好处是这允许派生类使用另一个签名来屏蔽这两种方法。使用
using手动提升这两种方法可以启动适当的重载解决方案,但如果您有许多具有此行为的方法,则无济于事。您的示例显示了我喜欢的模板用法,但不适合以前的语言,当时必须显式命名两个基类。
标签: c++ c++11 multiple-inheritance ambiguous name-lookup