天天看点

【机房重构】职责链模式之上机

【前言】

机房重构的过程是艰辛的呀,“磕磕绊绊”的终于到最后几个窗体了。敲学生上机,开始卡号就需要判断的条件很多,需要判断卡号是否存在,是否为“使用”状态;卡内的金额是够充足;该卡号是否在上机;如果还是按照以前的方式,逐条的判断,七层来回走很多遍,想想都头大呢。通过总结前人的经验和与小伙伴交流,原来是运用到了“职责链模式”;现在我来分享一下,我对它的理解吧!

【What】

在软件开发中,某一个对象的请求可能会被多个对象处理,但每次最多只有一个对象处理该请求,对这类问题如果显示指定请求的处理对象,那么势必会造成请求与处理的紧耦合,为了将请求与处理解耦,我们可以使用职责链模式,它可以向多个处理对象提交请求,具体是否哪个对象进行处理则是在运行过程中动态指定的!

运用到生活中,一个小职工想要加薪,但是不同层次的领导负责的加薪额度不同,这就需要一级一级的往高层反馈,直到有一个领导处理了加薪请求!

【Where】

在以下场景下,可以考虑使用职责链模式

       1.一个系统的审批需要多个对象才能完成处理的情况下,例如请假、加薪系统

       2.代码中存在多个if--else 语句的情况下,此时可以考虑职责链模式进行重构。

【How】

既然理论介绍的这么多了,应该也有了基本的了解了,那怎么运用呢,理论加实践才是真理嘛!别着急,现在我就来分享一下我的实战经历!

职责链模式上机D层

public class SqlSeverOnLineDAL:IDAL.IOnLine
    {
        //上机时查看卡号是否存在,查看卡内余额和基本数据表中的余额,查看是否正在上机
     
       public List<Card> checkcard(Card cardno)   //首先查询卡号是否存在、状态是否为使用
       { 
            SqlParameter[]parameter={new SqlParameter("@cardno",cardno.CardNo),
                                     new SqlParameter("@status","使用")};
            string sql = "select * from Card_Info where [email protected] and [email protected]";
            DataTable table = SQLHelper.SqlHelper.ExecuteDataTable(sql, CommandType.Text, parameter);
            if (table.Rows.Count>0)
            {
               ConvertHelper ct1 = new ConvertHelper();//实例化类
               List<Card> list = new List<Card>();
               list= ct1.convertToList<Card>(table);
                
               return list ;
            }
            else
            {
                return null;
            }
       
       }

       public List<OnOffLine>  checkon(OnOffLine online)  //在上机表中检查该卡号是否正在上机
       {
           SqlParameter[] sqlparameter = { new SqlParameter("@cardno",online.CardNo),
                                           new SqlParameter("@offtime",online.offtime)};
           string sql = "select * from OnOffLineRecord where [email protected] and [email protected] ";
           DataTable table1 = SQLHelper.SqlHelper.ExecuteDataTable(sql, CommandType.Text,sqlparameter);
        
               ConvertHelper ct2 = new ConvertHelper();
               List<OnOffLine> list1 = new List<OnOffLine>();
               list1 = ct2.convertToList<OnOffLine>(table1);
               return list1;
          
       }

       public List<BasicInfoSet> checkmoney(BasicInfoSet money)  //查看基本表中至少上机余额,可以让学生的金额跟它比较
       {
         
           string sql = "select * from BasicData_Info";
           DataTable table = SQLHelper.SqlHelper.ExecSelect(sql ,CommandType.Text);
           ConvertHelper ct3 = new ConvertHelper();
           List<BasicInfoSet>list2=new List<BasicInfoSet>();
           list2 = ct3.convertToList<BasicInfoSet>(table);
           return list2;
           

职责链模式上机B层

public  abstract class HandlerBLL   //设置一个抽象类
        {
            protected HandlerBLL successor;
            public void SetSuccessor(HandlerBLL successor)  //设置继任者
            {
                this.successor = successor;
            }
            public abstract object   HandlerCheck(Card cardno, OnOffLine online);  //设置请求的抽象方法
        }

       public class CheckcardBLL : HandlerBLL   //子类1:确定卡号是否存在,使用是否为"使用"
        {
            public override object      HandlerCheck(Card cardno, OnOffLine online)  //对于父类抽象方法的重写    
            {
                Factory.OnLineFactory factory = new Factory.OnLineFactory();
                IDAL.IOnLine dt = factory.checkcard();
                List<Card> ds = dt.checkcard(cardno);
                if (ds.Count <= 0)
                {
                    MessageBox.Show("改卡号不存在,请重新输入!");
                    return false;
                }
                else
                {

                    return true;   //卡号存在,返到上一层
                }

            }
        }

       public class CheckMoneyBLL : HandlerBLL  //子类2:查询基本表中的最少金额和卡表中的余额进行判断,查看是否符合要求"
        {
            public override object  HandlerCheck(Card cardno, OnOffLine online)
            {
                //获取卡表中的余额
                Factory.OnLineFactory factory1 = new Factory.OnLineFactory();
                IDAL.IOnLine dt1 = factory1.checkcard();
                List<Card> ds1 = dt1.checkcard(cardno);


                //获取基本数据表的最少余额
                Factory.OnLineFactory factory2 = new Factory.OnLineFactory();
                IDAL.IOnLine dt2 = factory2.checkmoney();
                BasicInfoSet money = new BasicInfoSet();
                List<BasicInfoSet> ds2 = dt2.checkmoney(money);

                //对基本表中的余额与卡表中的余额进行对比
                int a = int.Parse(ds1[0].cash);
                int b = int.Parse(ds2[0].limitCash);

                if (a < b)
                {
                   
                    MessageBox.Show("卡内余额不足!");
                    return false;

                }
                else
                {
                    return successor.HandlerCheck(cardno, online); //余额充足,转到下一级
                }

            }


        }

       public class CheckOnBLL : HandlerBLL   //子类3:检查卡号是否在上机
        {
            public override object   HandlerCheck(Card cardno, OnOffLine online)
            {
                Factory.OnLineFactory factory = new Factory.OnLineFactory();
                IDAL.IOnLine dt3 = factory.checkon();       
                List<OnOffLine> ds3=dt3.checkon(online);
                
                            
                if (ds3.Count<0)
                {
                    return true; 
                 
                   
                }
                else
                {
                    return false;
                   
                }

            }


        }
           

职责链上机 Facade层

public object   CheckOnLine(Card cardno, OnOffLine online)
       {
           OnLineBLL.CheckcardBLL cardBLL = new OnLineBLL.CheckcardBLL();
           OnLineBLL.CheckMoneyBLL moneyBLL = new OnLineBLL.CheckMoneyBLL();
           OnLineBLL.CheckOnBLL onBLL = new OnLineBLL.CheckOnBLL();
           
           //设定继承者的链条
           cardBLL.SetSuccessor(moneyBLL);
           moneyBLL.SetSuccessor(onBLL);
           //第一个查询的为卡号
           return cardBLL.HandlerCheck(cardno, online);
           

职责链上机UI层

private void btnUp_Click(object sender, EventArgs e)
        {
            if (txtCardNo.Text == "")
            {
                MessageBox.Show("上机请输入卡号!");
            }

            else
            {
                LoginEntity.Card card = new LoginEntity.Card();  //实例化实体层
                LoginEntity.OnOffLine online = new LoginEntity.OnOffLine();

                Facade.OnLineFacade facade = new Facade.OnLineFacade(); //实例化外观层
                card.CardNo = txtCardNo.Text.ToString(); 
                online.CardNo = txtCardNo.Text.ToString();
                object result = facade.CheckOnLine(card, online);
                bool flag = Convert.ToBoolean(result);

                if (flag == true)
                {
                    LoginEntity.OnOffLine online1 = new LoginEntity.OnOffLine();
                    //增加基本数据表中的数据               
                    online1.CardNo = txtCardNo.Text.ToString();
                    string time = DateTime.Now.ToLongTimeString().ToString();
                    online1.ontime = time;
                    string data = DateTime.Now.ToShortDateString().ToString();
                    online1.ondata = data;
                    online1.IsCheck = "未结账";
                    online1.status = "使用";
                    Facade.OnLineFacade dt = new Facade.OnLineFacade();
                    dt.intsert(online1);

                    //将数据显示到窗体上
                    LoginEntity.CardStudent cardno = new LoginEntity.CardStudent(); 
                     cardno.cardNo = txtCardNo.Text.ToString();
                    Facade.ViewBalanceFacade facade1 = new Facade.ViewBalanceFacade();
                    DataTable userback = facade1.viewbalance(cardno);

                    if (userback.Rows.Count > 0)  //将数据返回到桌面
                    {
                        txtCardNo.Text = userback.Rows[0]["cardNo"].ToString();
                        txtStudentNo.Text = userback.Rows[0]["studentNo"].ToString();
                        txtName.Text = userback.Rows[0]["studentName"].ToString();
                        txtSex.Text = userback.Rows[0]["sex"].ToString();
                        txtDepartment.Text = userback.Rows[0]["department"].ToString();
                        txtCash.Text = userback.Rows[0]["cash"].ToString();
                        txtStatus.Text = userback.Rows[0]["status"].ToString();
                        txtOntime.Text = DateTime.Now.ToLongTimeString().ToString();
                        txtondate.Text = DateTime.Now.ToShortDateString().ToString();
                       
                        //获取当前上机时间
                        DateTime  date = DateTime.Now;   
                        txtNowtime.Text = date.ToString();
                       
                        //获取当前上机人数
                        LoginEntity.OnOffLine on = new LoginEntity.OnOffLine();
                        Facade.OnLineFacade ln = new Facade.OnLineFacade();
                        DataTable pe = ln.acquire();
                        int i = pe.Rows.Count;
                        txtOnlineNumber.Text = i.ToString();
                      
                        MessageBox.Show("上机成功!");
                    }
                    else
                    {
                        MessageBox.Show("条件不满足");
                    }

                }
           

【总结】

思路是很重要的,先理清楚思路,在敲代码,可以避免少走很多弯路呢! 还有就是要多和其他人交流,站在巨人的肩膀上,利用好现有的资源!

【机房重构】职责链模式之上机