设计模式- 策略模式

定义

策略模式定义一系列算法,把它们一个个封装起来,并且使它们可互相替换,该模式使得算法可独立于使用它的客户而变化。

动机

 在软件构建过程中,某些对象使用的算法可能多种多样,经常改变,如果将这些算法都编码到对象中,将会使对象变得异常复杂;而且有时候支持不使用的算法也是一个性能负担。如何在运行时根据需要透明地更改对象的算法?将算法与对象本身解耦,从而避免上述问题?看下面的策略者模式的结构图和基本代码,策略者模式比较简单,下面只是给出基本的代码实现。

策略者模式结构图

 

策略模式的定义说的实在太抽象了,可能你读过去的时候捉不住他的要点。在大话设计模式里这么说的,更好理解一些:策略模式是一种定义了一系列算法的方法,所有这些算法完成的都是相同的工作,只是实现不同,它可以以相同的方式调用所有的算法,减少了各种算法类与使用算法类之间的耦合。

我们可以试着紧紧捉住这一句:所有这些算法完成的都是相同的工作,只是实现不同。

当有这种情况的有时候我们可以考虑一下使用策略模式。当然策略模式的使用是在需要实现比较大的,具有比较多的完成相同的工作,只是实现不同的情况下使用。如果只是一个或者两个的相同工作,实现算法不同的情况,那我想大多数人都只是改一下方法名就可以了。

 

这次通过两段代码来对策略模式了解

1、第一个例子是策略者模式的经典实现,类似于一个模型代码那样,百度一下你都能找到。

namespace 策略模式
{
    class Program
    {
        static void Main(string[] args)
        {
            Context ct = null;
            ct = new Context(new ConcretestrategyA());
            ct.ContextInterface();

            ct = new Context(new ConcretestrategyB());
            ct.ContextInterface();

            Console.ReadLine();
        }
    }

    /// <summary>
    /// 抽象算法类
    /// </summary>
    public abstract class Strategy
    {
        public abstract void AlgorithmInterface();
    }

    /// <summary>
    /// 算法A的实现
    /// </summary>
    public class ConcretestrategyA : Strategy
    {
        public override void AlgorithmInterface()
        {
            Console.WriteLine("算法A的实现");
        }
    }

    /// <summary>
    /// 算法B的实现
    /// </summary>
    public class ConcretestrategyB : Strategy
    {
        public override void AlgorithmInterface()
        {
            Console.WriteLine("算法B的实现");
        }
    }

    /// <summary>
    /// 上下文
    /// </summary>
    public class Context
    {
        private Strategy st;
        public Context(Strategy st)
        {
            this.st = st;
        }

        public void ContextInterface()
        {
            st.AlgorithmInterface();
        }
    }
}

2、第二个例子是新闻分页的,我们有两种分页的算法,一种使用的SQL语句是TOP的,另一种使用的是ROW_NUMBER。他们返回的分页结果相同,但是算法不同。(只是大概的实现,具体代码的实现细节不去考虑)

namespace 策略模式
{
    class Program
    {
        static void Main(string[] args)
        {
            Context ct = null;
            ct = new Context(new ConcretestrategyA());
            ct.ContextInterface(1,5);

            Console.WriteLine("----------------------------------------------");

            ct = new Context(new ConcretestrategyB());
            ct.ContextInterface(1,5);

            Console.ReadLine();
        }
    }

    /// <summary>
    /// 抽象算法类
    /// </summary>
    public abstract class Strategy
    {
        public abstract void GetPage(int pageIndex, int PageSize);
    }

    /// <summary>
    /// 算法A的实现
    /// </summary>
    public class ConcretestrategyA : Strategy
    {
        public override void GetPage(int pageIndex, int PageSize)
        {
            using (SqlConnection conn = new SqlConnection("server=.;database=test;uid=sa;pwd=123456"))
            {
                conn.Open();
                string strSql = @"SELECT TOP " + PageSize + " * FROM Customer WHERE id NOT IN(SELECT TOP " + PageSize * (pageIndex - 1) + " id FROM Customer ORDER BY id) ORDER BY id";
                using (SqlCommand cmd = new SqlCommand(strSql, conn))
                {
                    SqlDataReader dr = cmd.ExecuteReader();
                    while (dr.Read())
                    {
                        Console.WriteLine(string.Format("姓名:{0}  电话{1}", dr["cName"].ToString(), dr["cPhone"].ToString()));
                    }
                }
            }
        }
    }

    /// <summary>
    /// 算法B的实现
    /// </summary>
    public class ConcretestrategyB : Strategy
    {
        public override void GetPage(int pageIndex, int PageSize)
        {
            using (SqlConnection conn = new SqlConnection("server=.;database=test;uid=sa;pwd=123456"))
            {
                conn.Open();
                string strSql = @"select * from (select ROW_NUMBER() over(order by id) as RowNumer,* from Customer)t where t.RowNumer>" + (pageIndex - 1) * PageSize + " and t.RowNumer<=" + pageIndex * PageSize;
                using (SqlCommand cmd = new SqlCommand(strSql, conn))
                {
                    SqlDataReader dr = cmd.ExecuteReader();
                    while (dr.Read())
                    {
                        Console.WriteLine(string.Format("姓名:{0}  电话{1}", dr["cName"].ToString(), dr["cPhone"].ToString()));
                    }
                }
            }
        }
    }

    /// <summary>
    /// 上下文
    /// </summary>
    public class Context
    {

        private Strategy st;
        public Context(Strategy st)
        {
            this.st = st;
        }

        public void ContextInterface(int pageIndex,int pageSize)
        {
            st.GetPage(pageIndex, pageSize);
        }
    }
}


 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值