关于桥接模式实现的问题
Posted
技术标签:
【中文标题】关于桥接模式实现的问题【英文标题】:Question about Bridge Pattern implementation 【发布时间】:2020-10-28 04:22:53 【问题描述】:最近,我多次尝试理解桥接模式。不同的网站试图以不同的方式解释这个概念,但我开始理解这种模式——将抽象和实现解耦——允许我们进行不同类型的实现,此外,我们能够扩展我们的接口。但我只想确定一件事 - 基于以下示例:
#include <iostream>
class Device
protected:
int volume_m 0 ;
public:
int getVolume()
return volume_m;
void setVolume(int value)
volume_m = value;
;
class RemoteController
private:
std::shared_ptr<Device> device_m;
public:
RemoteController(std::shared_ptr<Device> device) : device_m(device)
void volumeUp()
device_m->setVolume(device_m->getVolume()+10);
std::cout << "Volume turned up. Current volume: " << device_m->getVolume() << '\n';
void volumeDown()
this->device_m->setVolume(this->device_m->getVolume() - 10);
std::cout << "Volume turned down. Current volume: " << device_m->getVolume() << '\n';
;
class TV : public Device
;
class Radio : public Device
;
int main()
std::shared_ptr<Device> tv = std::make_shared<TV>();
std::shared_ptr<RemoteController> controller = std::make_shared<RemoteController>(tv);
controller->volumeUp();
controller->volumeUp();
controller->volumeUp();
如果我想为TV
和Radio
发送不同的消息怎么办?我应该在Device
中创建名为volumeUp()
和volumeDown()
的虚拟方法,它们将被Radio
和TV
继承吗?而RemoteController
只会调用这些虚方法?
【问题讨论】:
【参考方案1】:是的,我相信在Radio
和TV
对象中实现VolumeUp
VolumeDown
方法会更正确。因为它们可能会因这些对象而有所不同(这两个对象都不是第 10 步)。
而且我认为最好不要在没有太多需要的情况下通过 getter 和 setter 公开你的实现。更多关于这个here
【讨论】:
【参考方案2】:我应该在
Device
中创建名为volumeUp()
和volumeDown()
的虚拟方法,它们将被Radio
和TV
继承吗?而RemoteController
只会调用这些虚方法?
是的,简而言之,桥接模式使用委托。 RemoteController
委托给Device
接口定义的成员函数。 TV
和 Radio
可以覆盖 Device
的虚成员函数。
委托是因为桥接模式依赖于组合。为了理解它为什么使用组合,让我们首先看一个没有利用桥接模式的例子。
单类层次结构示例 - 无桥
您有两种不同类型的设备:电视和收音机。假设您有两个不同的遥控器:射频和红外线控制器。然后,您总共将有四个类:RadioIRController
、RadioRFController
、TVIRController
、TVRFController
。这些类将实现一个接口RemoteController
,它指定了虚拟成员函数volumeUp()
和volumeDown()
,即一个单一的层次结构(即RemoteController
)。
在这个设计中,如果您现在想要添加一种新的遥控器,例如,超声波控制器,您必须创建两个额外的类:RadioUSController
和 TVUSController
.如果您想添加一种新的设备,例如,家庭立体声系统,则需要创建三个额外的类:HomeStereoIRController
、HomeStereoRFController
和 @987654348 @。
如您所见,扩展此设计很乏味。这是因为两个正交属性——设备类型和遥控器——混合在一个类层次结构中。这是切换到桥接模式的强烈动机。
应用桥接模式
您将单个层次结构分成两部分:Controller
和 Device
。这样,每个层次结构都可以相互独立地扩展。
我们通过部分放弃继承、拥抱组合和依赖委托来做到这一点:RemoteController
引用 Device
并调用此 Device
对象上的操作。
扩展此设计以额外支持家庭立体声系统只需要创建一个新类HomeStereo
,它继承自Device
。同样,扩展此设计以支持超声波控制器只需要创建一个新类USController
,它继承自RemoteController
。您现在可以轻松看出差异。
【讨论】:
以上是关于关于桥接模式实现的问题的主要内容,如果未能解决你的问题,请参考以下文章