大话设计模式笔记之---依赖倒置原则

依赖倒置原则(Dependence Inversion Principle,DIP)
又名”面向接口编程”

High level moudules should not depend upon low level modules.Both should depend upon abstractions.Absteactions should not depend upon details.Details should depend upon abstractions.

1.高层模块不应该依赖低层模块,两者都依赖其抽象;
2.抽象不应该依赖细节;
3.细节应该依赖抽象。

代码清单3——1 司机源代码
publi class Driver{
//司机的主要职责就是驾驶汽车
public void driver(Benz benz){
benz,run();
}
}
代码清单3-2 奔驰车源代码
public class Benz{
//汽车肯定会跑
public void run(){
System.out.println(“奔驰汽车开始运行…”);
}
}
代码清单3-3场景类源代码
public class Client{
public static void main(String [] args){
Driver zhangSan=new Driver();
Benz benz=new Benz();
//张三开奔驰车
zhangSan.drive(benz);
}
}
代码清单3-4宝马车源代码
public class BWM{
//宝马车当然可以开动了
public void run(){
System.out.println(“宝马汽车开始运行…);
}
}
代码清单3-5司机接口
public interface IDriver{
//司机就应该会驾驶汽车
public void driver(ICar car);
}
代码清单3-6司机类实现
public class Driver implements IDriver{
//司机的主要职责就是驾驶汽车
public void drive(Icar car){
car.run()
}
}
代码清单3-7汽车接口及两个实现类
public interface ICar{
//是汽车就应该能跑
public void run();
}

public class Benz implements ICar{
//奔驰车肯定会跑
public void run(){
System.out.println(“奔驰汽车开始运行…”);
}
}

public class BMW implements ICar{
//宝马车当然也可以开动了
public void run(){
System.out.println(“宝马汽车开始运行…”);
}
}

代码清单3-8业务场景
public class Client{
public static void main(String[] args){
IDriver zhangSan=new Driver();
ICar benz=new Benz();
//张三开奔驰车
zhnagSan.driver(benz);
}
}

代码清单3-9张三驾驶宝马的实现过程
public class Client{
public static void main(String[] args){
IDriver zhangSan=new Driver();
ICar bmw=new BMW();
//张三开宝马车
zhnagSan.driver(bmw);
}
}
代码清单3-10测试类
public class DriverTest extends TestCase{
Mockery context=new JUnit4Mockery();
@Test
public void testDriver(){
//根据接口虚拟一个对象
final ICar car=context.mock(ICar.class);
IDriver driver=new Driver();
//内部类
context.checking(new Expectations(){{
oneOf(car).run();
}});
driver.driveL(car);
}
}

对象的依赖关系有三种方式来传递
1.构造函数传递依赖对象(构造函数注入)
代码清单3-11构造函数传递对象依赖
public interface IDriver{
//司机就应该会驾驶汽车
public void drive();
}

public class Driver implements IDriver{
private ICar car;
//构造函数注入
public Driver(ICar _car){
this.car=_car;
}
//司机的主要职责就是驾驶汽车
public void driver(){
this.car.run();
}
}
2.Setter 方法传递依赖对象( Setter依赖注入)
代码清单3-13 Setter依赖注入
public interface IDriver{
//车辆型号
public void setCar(ICar car);
//是司机就应该会驾驶汽车
public void drive();
}

public class Driver implements IDriver{
private ICar car;
public void setCar(ICar car){
this.car=car;
}
//司机的主要职责就是驾驶汽车
public void drive(){
this.car.run();
}
}

3.接口声明依赖对象(接口注入)

例子:3-5司机接口

3.4如何使用DIP
1.每个类尽量都有接口或抽象类,或者抽象类和接口两者都具备
2.变量的表面类型尽量是接口或者是抽象类
3.任何类都不应该从具体类派生
4.尽量不要覆写基类的方法
5.结合里氏替换原则使用

你可能感兴趣的:(设计模式)