C# 设计模式-策略模式

策略模式-定义了算法族,分别封装起来,让它们相互之间可以替换。

对于客户的可能变化的行为采用组合的方式而非继承的方式。组合可以更加灵活的使用,而继承应对接口变化时太过繁琐。


下面用代码说明:

先定义一个抽象基类Car,所有实体车都要继承这个抽象基类

    public abstract class Car
    {
        //能跑
        public void Run()
        {
            Console.WriteLine("i can run");
        }
        //打印品牌
        public abstract void Brand();
    }

定义奔驰、宝马

    public class Benz : Car
    {
        public override void Brand()
        {
            Console.WriteLine("奔驰");
        }
    }

    public class Bmw:Car
    {
        public override void Brand()
        {
            Console.WriteLine("宝马");
        }
    }

现在奔驰要装倒车雷达,但是宝马不装(说不定以后要装,甚至还要装全身雷达)。

方案1:建立一个雷达接口,Car继承。但是这会让每辆车都有一个雷达。可以在每个实体类中重写,但是后期需求改变,就得改这个类了。

方案2:建立一个雷达接口,由实体类继承。也不太好,原因和上面一样。

方案3:建立一个雷达接口,不在用继承的方式,而采用组合的方式。不需要在类中具体实现,可以在外部实现接口,做到松耦合。

接下来采用方案三来重写。

    public interface IRadar
    {
        void Radar();
    }

    public abstract class Car
    {
        public IRadar Radar{ get; set; }
        //能跑
        public void Run()
        {
            Console.WriteLine("i can run");
        }
        //打印品牌
        public abstract void Brand();
        //展示雷达
        public void Perform()
        {
            Radar.Radar();
        }
    }

实现雷达实体类

    public class NoRadar : IRadar
    {
        public void Radar()
        {
            Console.WriteLine("我没有雷达");
        }
    }

    public class ParkingRadar : IRadar
    {
        public void Radar()
        {
            Console.WriteLine("我是倒车雷达");
        }
    }

    public class GeneralRadar : IRadar
    {
        public void Radar()
        {
            Console.WriteLine("我是全身雷达");
        }
    }
    public class Benz : Car
    {
        //默认没有雷达
        public Benz()
        {
            Radar = new NoRadar();
        }

        public override void Brand()
        {
            Console.WriteLine("奔驰");
        }
    }

    public class Bmw:Car
    {
        public Bmw()
        {
            Radar = new NoRadar();
        }

        public override void Brand()
        {
            Console.WriteLine("宝马");
        }
    }

调用

    class Program
    {
        static void Main(string[] args)
        {
            Car benz = new Benz();
            benz.PerformRadar();
            //给奔驰加上雷达
            benz.Radar = new ParkingRadar();
            benz.PerformRadar();

            Car bmw = new Bmw();
            bmw.PerformRadar();

            Console.ReadLine();
        }
    }

结果

我们默认奔驰和宝马初始都是没有雷达的,这不太好,可能现在倒车雷达成标配了,出厂就自带,所以我们把默认的不带雷达要改成倒车雷达,随着需求的改动,我们需要不断的改变我们的实体类,这又不太好了。所以我们改成创建时决定

修改宝马和奔驰

    public class Benz : Car
    {
        public Benz(IRadar radar)
        {
            Radar = radar;
        }

        public override void Brand()
        {
            Console.WriteLine("奔驰");
        }
    }

    public class Bmw:Car
    {
        public Bmw(IRadar radar)
        {
            Radar = radar;
        }

        public override void Brand()
        {
            Console.WriteLine("宝马");
        }
    }

调用

        static void Main(string[] args)
        {
            Car benz = new Benz(new ParkingRadar());
            benz.PerformRadar();

            Car bmw = new Bmw(new GeneralRadar());
            bmw.PerformRadar();

            Console.ReadLine();
        }

结果

出厂自带,想升级也十分方便,将Rador改成全身雷达即可


在策略模式下,我们的车不论有没有雷达,安装什么雷达,我都不关心了,你决定有就有,你决定没有就没有,我只要调用PerformRador即可,是不是很方便。

当然,如果你想新增加一套自动驾驶系统,我们的实体类的代码是肯定需要改的,但是方法和雷达一样,只需要再添加一个自动驾驶的接口即可。一旦建立了自动驾驶的策略,在自动驾驶领域,无论怎么变,我都不会变。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值