微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

从通用基类继承多次时的歧义调用

如何解决从通用基类继承多次时的歧义调用

我想克隆一个包含几种类型的std::list的数据结构,并同时移动一些迭代器以指向新的std::list的元素。为此,我创建了一个通用类型Translate<T>,它表示从旧列表中的std::list<T>::iterator到新列表中的映射。然后,对于我的数据结构中所有需要的类型Translate<T>我有一个T继承的新类。

这是一个简化的示例(仅使用身份函数):

#include <list>

struct T1 {};
struct T2 {};

template<typename T>
class Translate {
    public:
    typename std::list<T>::iterator operator()(typename std::list<T>::iterator x) {
        return x; // more complex in the real world,but doesn't matter here
    }
};

int main() {
    std::list<T1> l1{};
    std::list<T2> l2{};

    class : public Translate<T1>,public Translate<T2> {} tr;
    tr(l1.begin());
}

这给了我下面的编译器错误

mwe.cpp: In function ‘int main()’:
mwe.cpp:19:15: error: request for member ‘operator()’ is ambiguous
  tr(l1.begin());
               ^
mwe.cpp:9:34: note: candidates are: ‘typename std::__cxx11::list<T>::iterator Translate<T>::operator()(typename std::__cxx11::list<T>::iterator) [with T = T2; typename std::__cxx11::list<T>::iterator = std::_List_iterator<T2>]’
  typename std::list<T>::iterator operator()(typename std::list<T>::iterator x) {
                                  ^~~~~~~~
mwe.cpp:9:34: note:                 ‘typename std::__cxx11::list<T>::iterator Translate<T>::operator()(typename std::__cxx11::list<T>::iterator) [with T = T1; typename std::__cxx11::list<T>::iterator = std::_List_iterator<T1>]’

该呼叫的歧义是什么? std::list<T>::iterator不能相互转换。

如果我将每个T的实现手动复制到子类中,它将起作用,但这正是使用泛型和继承时要避免的事情。

解决方法

此代码格式错误。如果operator()在派生类中不可用,则名称查找仅在恰好一个基类的情况下才考虑基类。如果存在多个基类,则名称查找中将考虑个基类。

如前所述,您可以将operator()的实现复制到派生类中,并且可以正常工作,但是您也可以将两个operator()名称都用{ {1}}指令,如下所示:

using

这里是demo

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。