【前言】
机房重构的过程是艰辛的呀,“磕磕绊绊”的终于到最后几个窗体了。敲学生上机,开始卡号就需要判断的条件很多,需要判断卡号是否存在,是否为“使用”状态;卡内的金额是够充足;该卡号是否在上机;如果还是按照以前的方式,逐条的判断,七层来回走很多遍,想想都头大呢。通过总结前人的经验和与小伙伴交流,原来是运用到了“职责链模式”;现在我来分享一下,我对它的理解吧!
【What】
在软件开发中,某一个对象的请求可能会被多个对象处理,但每次最多只有一个对象处理该请求,对这类问题如果显示指定请求的处理对象,那么势必会造成请求与处理的紧耦合,为了将请求与处理解耦,我们可以使用职责链模式,它可以向多个处理对象提交请求,具体是否哪个对象进行处理则是在运行过程中动态指定的!
运用到生活中,一个小职工想要加薪,但是不同层次的领导负责的加薪额度不同,这就需要一级一级的往高层反馈,直到有一个领导处理了加薪请求!
【Where】
在以下场景下,可以考虑使用职责链模式
1.一个系统的审批需要多个对象才能完成处理的情况下,例如请假、加薪系统
2.代码中存在多个if--else 语句的情况下,此时可以考虑职责链模式进行重构。
【How】
既然理论介绍的这么多了,应该也有了基本的了解了,那怎么运用呢,理论加实践才是真理嘛!别着急,现在我就来分享一下我的实战经历!
职责链模式上机D层
public class SqlSeverOnLineDAL:IDAL.IOnLine
{
//上机时查看卡号是否存在,查看卡内余额和基本数据表中的余额,查看是否正在上机
public List checkcard(Card cardno) //首先查询卡号是否存在、状态是否为使用
{
SqlParameter[]parameter={new SqlParameter("@cardno",cardno.CardNo),
new SqlParameter("@status","使用")};
string sql = "select * from Card_Info where CardNo=@cardno and status=@status";
DataTable table = SQLHelper.SqlHelper.ExecuteDataTable(sql, CommandType.Text, parameter);
if (table.Rows.Count>0)
{
ConvertHelper ct1 = new ConvertHelper();//实例化类
List list = new List();
list= ct1.convertToList(table);
return list ;
}
else
{
return null;
}
}
public List checkon(OnOffLine online) //在上机表中检查该卡号是否正在上机
{
SqlParameter[] sqlparameter = { new SqlParameter("@cardno",online.CardNo),
new SqlParameter("@offtime",online.offtime)};
string sql = "select * from OnOffLineRecord where CardNo=@cardno and offtime=@offtime ";
DataTable table1 = SQLHelper.SqlHelper.ExecuteDataTable(sql, CommandType.Text,sqlparameter);
ConvertHelper ct2 = new ConvertHelper();
List list1 = new List();
list1 = ct2.convertToList(table1);
return list1;
}
public List checkmoney(BasicInfoSet money) //查看基本表中至少上机余额,可以让学生的金额跟它比较
{
string sql = "select * from BasicData_Info";
DataTable table = SQLHelper.SqlHelper.ExecSelect(sql ,CommandType.Text);
ConvertHelper ct3 = new ConvertHelper();
Listlist2=new List();
list2 = ct3.convertToList(table);
return list2;
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 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 ds1 = dt1.checkcard(cardno);
//获取基本数据表的最少余额
Factory.OnLineFactory factory2 = new Factory.OnLineFactory();
IDAL.IOnLine dt2 = factory2.checkmoney();
BasicInfoSet money = new BasicInfoSet();
List 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 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);
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("条件不满足");
}
}
【总结】
思路是很重要的,先理清楚思路,在敲代码,可以避免少走很多弯路呢! 还有就是要多和其他人交流,站在巨人的肩膀上,利用好现有的资源!