C++多重继承和鸭子类型
C++ multiple inheritance and duck typing
我正在尝试找到一种方法来为继承一对相似接口的两个对象表达共同的基类型。
参见下面的代码:显然 fb1 和 fb2 应该有一个可能的公共基类型(例如,类似 IFizzBuzz 的类型)。
有谁知道这是否可行(如果可能不需要模板:-)
谢谢!
#include <memory>
#include <iostream>
struct IFizz {
virtual void DoFizz() = 0;
};
struct IBuzz {
virtual void DoBuzz() = 0;
};
struct Fizz : public IFizz {
void DoFizz() override {
std::cout << "Fizz\n";
}
};
struct Buzz1 : public IBuzz {
void DoBuzz() override {
std::cout << "Buzz1\n";
}
};
struct Buzz2 : public IBuzz {
void DoBuzz() override {
std::cout << "Buzz2\n";
}
};
struct FizzBuzz1 : public Fizz, public Buzz1 {
};
struct FizzBuzz2 : public Fizz, public Buzz2 {
};
// Expected "Base type" of FizzBuzz1 and FizzBuzz2
struct IFizzBuzz : public IFizz, public IBuzz {
};
int main()
{
{
FizzBuzz1 fb1;
fb1.DoFizz();
fb1.DoBuzz();
}
{
FizzBuzz2 fb2;
fb2.DoFizz();
fb2.DoBuzz();
}
// {
// // The line below is not legit and does not compile
// std::unique_ptr<IFizzBuzz> ifb(new FizzBuzz1());
// ifb->DoFizz();
// ifb->DoBuzz();
// }
return 0;
}
FizzBuzz1
和 FizzBuzz2
有 3 个公共碱基 class
IFizz
IBuzz
Fizz
如果不改变这两个的定义,就无法让它们也以IFizzBuzz
为基础。
然而,您可以有一个 class 派生 IFizzBuzz
并委托给两者之一,例如
template <typename FizzBuzz>
struct Wrapper : IFizzBuzz
{
void DoFizz() final { fizzBuzz.DoFizz(); }
void DoBuzz() final { fizzBuzz.DoBuzz(); }
private:
FizzBuzz fizzBuzz;
}
这就可以使用了,例如
std::unique_ptr<IFizzBuzz> ifb = std::make_unique<Wrapper<FizzBuzz1>>();
ifb->DoFizz();
ifb->DoBuzz();
ifb = std::make_unique<Wrapper<FizzBuzz2>>();
ifb->DoFizz();
ifb->DoBuzz();
我正在尝试找到一种方法来为继承一对相似接口的两个对象表达共同的基类型。
参见下面的代码:显然 fb1 和 fb2 应该有一个可能的公共基类型(例如,类似 IFizzBuzz 的类型)。
有谁知道这是否可行(如果可能不需要模板:-)
谢谢!
#include <memory>
#include <iostream>
struct IFizz {
virtual void DoFizz() = 0;
};
struct IBuzz {
virtual void DoBuzz() = 0;
};
struct Fizz : public IFizz {
void DoFizz() override {
std::cout << "Fizz\n";
}
};
struct Buzz1 : public IBuzz {
void DoBuzz() override {
std::cout << "Buzz1\n";
}
};
struct Buzz2 : public IBuzz {
void DoBuzz() override {
std::cout << "Buzz2\n";
}
};
struct FizzBuzz1 : public Fizz, public Buzz1 {
};
struct FizzBuzz2 : public Fizz, public Buzz2 {
};
// Expected "Base type" of FizzBuzz1 and FizzBuzz2
struct IFizzBuzz : public IFizz, public IBuzz {
};
int main()
{
{
FizzBuzz1 fb1;
fb1.DoFizz();
fb1.DoBuzz();
}
{
FizzBuzz2 fb2;
fb2.DoFizz();
fb2.DoBuzz();
}
// {
// // The line below is not legit and does not compile
// std::unique_ptr<IFizzBuzz> ifb(new FizzBuzz1());
// ifb->DoFizz();
// ifb->DoBuzz();
// }
return 0;
}
FizzBuzz1
和 FizzBuzz2
IFizz
IBuzz
Fizz
如果不改变这两个的定义,就无法让它们也以IFizzBuzz
为基础。
然而,您可以有一个 class 派生 IFizzBuzz
并委托给两者之一,例如
template <typename FizzBuzz>
struct Wrapper : IFizzBuzz
{
void DoFizz() final { fizzBuzz.DoFizz(); }
void DoBuzz() final { fizzBuzz.DoBuzz(); }
private:
FizzBuzz fizzBuzz;
}
这就可以使用了,例如
std::unique_ptr<IFizzBuzz> ifb = std::make_unique<Wrapper<FizzBuzz1>>();
ifb->DoFizz();
ifb->DoBuzz();
ifb = std::make_unique<Wrapper<FizzBuzz2>>();
ifb->DoFizz();
ifb->DoBuzz();