如果派生类定义了相同的名称,则派生类对基类隐藏重载集的名称,但是我们始终可以使用using-declaration将该重载集重新引入:
template <class BASE>
class A : public BASE
{
public:
using BASE::some_method;
void some_method();
}
但是,如果我引入可变参数基类的所有重载集,该怎么办?
我可以写这样的东西吗?
template <class... BASES>
class A : public BASES...
{
public:
using BASES::some_method...;
void some_method();
}
我考虑过使用像这样的帮助器类:
template <class... BASES>
struct helper;
template <>
struct helper<> {};
template <class OnlyBase>
struct helper<OnlyBase> : OnlyBase
{
using OnlyBase::some_method;
};
template <class Base1, class... OtherBases>
struct helper<Base1, OtherBases> : public Base1, public helper<OtherBases...>
{
using Base1::some_method;
using helper<OtherBases...>::some_method;
};
它确实有效。但这需要大量的输入(当然我可以使用宏,但是我会尽可能使用c++的编译时功能),并且当我想引入更多的方法时,我必须在那段代码中进行很多更改。
完美的答案将是简单的语法,但是如果没有语法,我将使用帮助程序类。
最佳答案
这是减少笔迹的技巧:
// U<X,Y> is a binary operation on two classes
template<template<class,class>class U, class... Xs> struct foldr;
template<template<class,class>class U, class X> struct foldr<U,X> : X {};
template<template<class,class>class U, class X, class... Xs> struct foldr<U,X,Xs...> : U<X, foldr<U,Xs...>> {};
// our operation inherits from both classes and declares using the member f of them
template<class X, class Y> struct using_f : X,Y { using X::f; using Y::f; };
struct A { void f(int) {} };
struct B { void f(char) {} };
struct C { void f(long) {} };
struct D : foldr<using_f, A, B, C> {};
int main() {
D d;
d.f(1);
d.f('1');
d.f(1L);
return 0;
}
因此,我们应该编写一次foldr,然后编写简单的即席操作-using_f,using_g,using_f_g
也许有一种方法可以进一步简化。我想一想...