优点:处理多层继承结构,处理多维度的变化场景,解耦,提高扩展性,隐藏实现细节。
缺点:增加系统的理解和设计难度,由于聚合关联关系建立在抽象层,需要针对抽象设计、编程,还要识别出系统独立变化的维度。
以运动鞋做例子,鞋子分足球鞋,篮球鞋等,还分各种品牌,耐克,阿迪达斯等。
列子:在没有使用桥接模式情况下处理运动鞋的关系,看下有多麻烦。
/**
* 这是一个运动鞋接口,包含实现类以及继承类
*/
public interface SportsShoes {
void sales();
}
/**
* 篮球鞋实体类,并实现SportsShoes接口
*/
class BasketballShoes implements SportsShoes {
@Override
public void sales() {
Log.d("TAG", "销售篮球鞋");
}
}
/**
* 足球实体类,并实现SportsShoes接口
*/
class SoccerShoes implements SportsShoes {
@Override
public void sales() {
Log.d("TAG", "销售足球鞋");
}
}
/**
* Nike篮球鞋实体类,并继承篮球鞋接口
*/
class NikeBasketballShoes extends BasketballShoes {
@Override
public void sales() {
Log.d("TAG", "销售Nike篮球鞋");
}
}
/**
* Nike足球鞋实体类,并继承足球鞋接口
*/
class NikeSoccerShoes extends SoccerShoes {
@Override
public void sales() {
Log.d("TAG", "销售Nike足球鞋鞋");
}
}
/**
* Adidas篮球鞋实体类,并继承篮球鞋接口
*/
class AdidasBasketballShoes extends BasketballShoes {
@Override
public void sales() {
Log.d("TAG", "销售Adidas篮球鞋");
}
}
/**
* Adidas足球鞋实体类,并继承足球鞋接口
*/
class AdidasSoccerShoes extends SoccerShoes {
@Override
public void sales() {
Log.d("TAG", "销售Adidas足球鞋鞋");
}
}
调用:
/**
* 这是调用者
*/
public class MainActivity extends FragmentActivity {
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//销售Nike篮球运动鞋
BasketballShoes nike = new NikeBasketballShoes();
nike.sales();
}
}

这样做的问题:
1.扩展问题(类个数膨胀):如果需要新增一个跑步鞋,则需要新增各个品牌下边的类,如果需要新增一个安踏品牌,则需要新增各种类型下的类,比如篮球鞋,足球鞋,跑鞋等等......
2.违反设计模式六大原则中的单一职责原则(有两个引起类变化的原因,一个是品牌,一个是类型)
桥接模式
把它们分成两个维度,一个是品牌,一个是运动鞋
创建一个品牌接口:
/**
* 这是一个品牌接口
*/
public interface Brand {
void sales();
}
创建一个Nike实体类,并实现Brand接口:
/**
* Nike品牌
*/
public class Nike implements Brand {
@Override
public void sales() {
Log.d("TAG","销售Nike");
}
}
创建一个Adidas实体类,并实现Brand接口:
/**
* Adidas实体类
*/
public class Adidas implements Brand {
@Override
public void sales() {
Log.d("TAG", "销售Adidas");
}
}
创建运动鞋类:
/**
* 这是一个运动鞋类,以此类做为桥梁
*/
public class SportsShoes2 {
protected Brand brand; //把品牌维度作为属性,与运动鞋维度相关联,形成他们之间沟通的桥梁
public SportsShoes2(Brand brand) {
this.brand = brand;
}
public void sales() {
brand.sales();
}
}
创建篮球鞋实体类:
/**
* 这是一个篮球鞋实体类
*/
public class BasketballShoes2 extends SportsShoes2 {
public BasketballShoes2(Brand brand) {
super(brand);
}
@Override
public void sales() {
super.sales();
Log.d("TAG","销售篮球鞋");
}
}
创建足球鞋实体类:
/**
* 这是一个足球实体类
*/
public class SoccerShoes2 extends SportsShoes2 {
public SoccerShoes2(Brand brand) {
super(brand);
}
@Override
public void sales() {
super.sales();
Log.d("TAG","销售足球鞋");
}
}
调用:
/**
* 这是调用者
*/
public class MainActivity extends FragmentActivity {
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//销售Nike篮球鞋
SportsShoes2 nike1 = new BasketballShoes2(new Nike());
nike1.sales();
//销售Nike足球鞋
SportsShoes2 nike2 = new SoccerShoes2(new Nike());
nike2.sales();
//销售Adidas篮球鞋
SportsShoes2 adidas1 = new BasketballShoes2(new Adidas());
adidas1.sales();
//销售Adidas足球鞋
SportsShoes2 adidas2 = new SoccerShoes2(new Adidas());
adidas2.sales();
}
}
结果:

如果我要增加一个跑步鞋类型,直接新增一个类型类就能实现,不需要再像先前一样还要给各个品牌新增类型。
/**
* 这是跑鞋类
*/
public class RunningShoes2 extends SportsShoes2 {
public RunningShoes2(Brand brand) {
super(brand);
}
@Override
public void sales() {
super.sales();
Log.d("TAG","销售跑步鞋");
}
}
调用:
/**
* 这是调用者
*/
public class MainActivity extends FragmentActivity {
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// //销售Nike篮球鞋
// SportsShoes2 nike1 = new BasketballShoes2(new Nike());
// nike1.sales();
//
// //销售Nike足球鞋
// SportsShoes2 nike2 = new SoccerShoes2(new Nike());
// nike2.sales();
//
//
// //销售Adidas篮球鞋
// SportsShoes2 adidas1 = new BasketballShoes2(new Adidas());
// adidas1.sales();
//
// //销售Adidas足球鞋
// SportsShoes2 adidas2 = new SoccerShoes2(new Adidas());
// adidas2.sales();
//销售Nike跑步鞋
SportsShoes2 nike = new RunningShoes2(new Nike());
nike.sales();
//销售Adidas跑步鞋
SportsShoes2 adidas = new RunningShoes2(new Adidas());
adidas.sales();
}
}
结果:

非常方便。
新增品牌也是一样逻辑。
安踏品牌:
/**
* 这是一个安踏品牌实体类
*/
public class Anta implements Brand{
@Override
public void sales() {
Log.d("TAG","销售安踏");
}
}
调用:
/**
* 这是调用者
*/
public class MainActivity extends FragmentActivity {
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// //销售Nike篮球鞋
// SportsShoes2 nike1 = new BasketballShoes2(new Nike());
// nike1.sales();
//
// //销售Nike足球鞋
// SportsShoes2 nike2 = new SoccerShoes2(new Nike());
// nike2.sales();
//
//
// //销售Adidas篮球鞋
// SportsShoes2 adidas1 = new BasketballShoes2(new Adidas());
// adidas1.sales();
//
// //销售Adidas足球鞋
// SportsShoes2 adidas2 = new SoccerShoes2(new Adidas());
// adidas2.sales();
// //销售Nike跑步鞋
// SportsShoes2 nike = new RunningShoes2(new Nike());
// nike.sales();
//
// //销售Adidas跑步鞋
// SportsShoes2 adidas = new RunningShoes2(new Adidas());
// adidas.sales();
//销售安踏篮球鞋
SportsShoes2 anta1 = new BasketballShoes2(new Anta());
anta1.sales();
//销售安踏足球鞋
SportsShoes2 anta2 = new SoccerShoes2(new Anta());
anta2.sales();
//销售安踏跑步鞋
SportsShoes2 anta3 = new RunningShoes2(new Anta());
anta3.sales();
}
}
结果:

已完成测试!有不对的地方欢迎指出,感恩。
网友评论