zoukankan      html  css  js  c++  java
  • 接口隔离原则实例

    违反接口隔离原则的例子一:
    我们假设一个人会开汽车卡车坦克(但是不会开炮),我们先设置以下类
    Vehicle类型

        interface IVehicle
        {
            void Run();
        }
    
        class Car:IVehicle
        {
            public void Run()
            {
                Console.WriteLine("Car is Running");
            }
        }
        class Truck:IVehicle
        {
            public void Run()
            {
                Console.WriteLine("Truck is Running");
            }
        }
    

    Tank类型

        interface ITank
        {
            void Fire();
            void Run();
        }
    
        class Type99 : ITank
        {
            public void Fire()
            {
                Console.WriteLine("Boom!");
            }
            public void Run()
            {
                Console.WriteLine("Ka!");
            }
        }
    

    这时候我们如果要人开Vehicle类的Car或者Truck,那么这个人就不能开Tank。

        class Driver
        {
            private IVehicle _vehicle;
            public Driver(IVehicle vehicle)
            {
                _vehicle = vehicle;
            }
            public void Drive()
            {
                _vehicle.Run();
            }
        }
    
        class Program
        {
            static void Main(string[] args)
            {
                var driver = new Driver(new Car());
                driver.Drive();
            }
        }
    

    如果让他开Tank,则他不能开Vehicle

        class Driver
        {
            private ITank _tank;
            public Driver(ITank tank)
            {
                _tank = tank;
            }
            public void Drive()
            {
                _tank.Run();
            }
        }
    
        class Program
        {
            static void Main(string[] args)
            {
                var driver = new Driver(new Type99());
                driver.Drive();
            }
        }
    

    仔细看会发现,type99(99式坦克)中的Fire()作为实例方法缺从未被使用过,违背了"类不应该被迫依赖他们不使用的方法"这条原则。

    Tank里面有作为Vehicle的Run()方法,和不属于Vehicle的Fire()方法。这使得Tank这个接口太大无法用Vehicle来囊括。
    解决方式是把Tank这个接口拆分成两个接口,
    分别是作为交通工具的IVehicle和作为武器的IWeapon。

    纠正方式:
    ITank接口去继承这两个接口,它就是简单的把这两个接口结合起来,这就是一个接口对其他多个接口的继承。
    C#中当类和类继承时,只允许存在一个父类(基类),但是当你拿一个类/接口去继承接口的时候,可以有多个父接口(基接口)

        interface IVehicle
        {
            void Run();
        }
        interface IWeapon
        {
            void Fire();
        }
    
        interface ITank:IVehicle,IWeapon
        {
        }
    
        class Type99 : ITank
        {
            public void Fire()
            {
                Console.WriteLine("Boom!");
            }
            public void Run()
            {
                Console.WriteLine("Ka!");
            }
        }
    
        class Program
        {
            static void Main(string[] args)
            {
                var drivercar = new Driver(new Car());
                drivercar.Drive();
                var drivertruck = new Driver(new Car());
                drivertruck.Drive();
                var drivertank = new Driver(new Type99());
                drivertank.Drive();
            }
        }
    

    这样就Car,Truck,Tank都可以开了。

  • 相关阅读:
    【LCA】BZOJ1832 & BZOJ1787(AHOI)-集会
    【线段树+离散化】POJ2528-Mayor's posters
    JavaScript Array 整理
    常见的原生javascript DOM操作
    javascript中执行环境和作用域(js高程)
    javascript作用域链
    javascript执行环境及作用域
    [转]深入javascript——原型链和继承
    [转]深入javascript——构造函数和原型对象
    Java接口中的成员变量为什么必须声明为public static final?
  • 原文地址:https://www.cnblogs.com/maomaodesu/p/11633824.html
Copyright © 2011-2022 走看看