多重继承中的歧义类成员

问题描述 投票:6回答:2

假设我有这个可变的基类模板:

template <typename ... Types>
class Base
{
public:
    // The member foo() can only be called when its template 
    // parameter is contained within the Types ... pack.

    template <typename T>
    typename std::enable_if<Contains<T, Types ...>::value>::type
    foo() {
        std::cout << "Base::foo()\n";
    }
};

foo()成员仅在其模板参数与Base的参数中的至少一个匹配时才可以调用(Contains的实现在本文的底部列出:]

Base<int, char>().foo<int>(); // fine
Base<int, char>().foo<void>(); // error

现在我使用类型的非重叠集定义从Base继承两次的派生类:

struct Derived: public Base<int, char>,
                public Base<double, void>
{};

我希望在例如致电时>

Derived().foo<int>();

编译器会找出要使用的基类,因为它是SFINAE,而不包含int。但是,GCC 4.9和Clang 3.5都抱怨调用不明确。

我的问题是双重的:

  1. 为什么编译器不能解决这种歧义(一般利益)?
  2. 无需写Derived().Base<int, char>::foo<int>();,我该怎么做才能完成这项工作? 编辑:
  3. GuyGreer告诉我,当我添加两个using-声明时,该呼叫已消除歧义。但是,由于我为用户提供了继承的基类,因此这不是理想的解决方案。如果有可能,我不希望我的用户必须将这些声明(对于大型类型列表可能是非常冗长和重复的)添加到其派生类中。

    Contains的实现:

template <typename T, typename ... Pack>
struct Contains;

template <typename T>
struct Contains<T>: public std::false_type
{};

template <typename T, typename ... Pack>
struct Contains<T, T, Pack ...>: public std::true_type
{};

template <typename T, typename U, typename ... Pack>
struct Contains<T, U, Pack ...>: public Contains<T, Pack...>
{};

假设我有这个可变的基类模板:template class Base {public://成员foo()仅在包含其模板//参数时才能被调用...

c++ c++11 multiple-inheritance ambiguity enable-if
2个回答
14
投票

这是一个简单的示例:


3
投票

尽管我不能详细告诉您为什么它不能按原样工作,但我在template <typename... Bases> struct BaseCollector : Bases... { using Bases::foo...; }; 上添加了using Base<int, char>::foo;using Base<double, void>::foo;,现在可以正常编译了。

© www.soinside.com 2019 - 2024. All rights reserved.