机房合作登录——装饰模式

      装饰模式: 主要用来实现动态的添加功能。这样可以使得在需要新的方法时可以直接的添加新的类,主类保持不变,符合设计模式中“开放封闭原则”。
      在机房收费的系统用户登录的过程中,可以使用装饰模式。在登录的时候我们分别需要验证用户名,密码,如果要求一个用户只能够登录一次,还需要验证用户的登录状态,如果都没有问题则用户进如系统的主界面。这里的“验证用户状态”就可以看做动态的功能,需要的时候就动态的加载上。
     首先以机房中的登录为例看一下装饰模式的类图。

LogingBLL就是要被装饰的主类,TestUserBLL是装饰类的抽象类,继承和实现LoginBLL的TestLogin方法,增加SetObject方法用来设置要装饰的对象。其他的三个类TestLoginStateBLL、UserExistBLL、TestLoginPWDBLL继承TestUserBLL类同时重写其中TestLogin方法。代码的实现如下:

public class LoginBLL<span style="white-space:pre">	</span>//要被装饰的对象
    {
        public LoginBLL()
        {
        }
        /// <summary>
        /// 检测用户是否可以登陆,抽象方法,必须重写
        /// </summary>
        /// <param name="enUser"></param>
        public virtual bool TestLogin(UserModel enUser)//需要被继承重新的方法
        {
            return true;
        }
}

public class TestUserBLL:LoginBLL<span style="white-space:pre">	</span>//继承LoginBLL这个要被装饰的类
    {
        protected LoginBLL declogin;//实例一个要被装饰的对象
        public TestUserBLL() { 
        }
        public TestUserBLL(UserModel enUser)
        {   
        }
        public void SetObject(LoginBLL declogin){<span style="white-space:pre">	</span>//该方法设置要装饰的对象
            this.declogin = declogin;      
 }
		/// <summary>
		/// 检测用户是否可以登陆
		/// </summary>
		/// <param name="enUser"></param>
        public override bool TestLogin(UserModel enUser)<span style="white-space:pre">	</span>//重新TestLogin,实质执行的是declogin的TestLogin方法
        {
            try
            {
                if (declogin != null)
                {//如果要装饰的对象不为空就调用被装饰对象的TestLogin方法进行检测                 
		    return declogin.TestLogin(enUser);
                }
                else
                {
                    return false;//如果要装饰的对象为空就直接的返回false
                }
            }
            catch (System.Exception)
            {
                
                throw new Exception("用户登录信息错误请重新输入!");


public class TestLoginStateBLL : TestUserBLL<span style="white-space:pre">	</span>//继承TestUserBLL重新TestLogin方法,主要用来检验要登录的用户的状态
    {
		public TestLoginStateBLL(){
		}
		/// <summary>
		/// 检测用户是否可以登陆——查询用户状态,已经登录返回false,抛出异常提示:用户已经在线,不可以重复登陆。未登录返回true。
		/// </summary>
		/// <param name="enUser"></param>
		public override bool TestLogin(UserModel enUser){
            bool flag = false;
            try
            {
                base.TestLogin(enUser); //先运行原来TestUserBLL的TestLoging,在执行自己的如下的方法
                CreateFactory factory = new CreateFactory();
                IUser userInter = factory.CreateUser();
                if (userInter.QueryById(enUser) ==true)<span style="white-space:pre">	</span>//调用B层相关方法进行检验
                {
                    flag = true;
                }
                else {
                    throw new Exception("用户已经在线,不可以重复登陆");<span style="white-space:pre">	</span>//检验失败则抛出错误
                }
            }
            catch (System.Exception)
            {
                throw new Exception("用户不存在,请重新输入用户名");
            }
            return flag;
			}
	}


public class TestLoginPWDBLL : TestUserBLL
    {
		/// <summary>
		/// 检测用户是否可以登陆_检测密码。密码正确返回true,否则返回false,抛出异常提示:登陆密码不正确,请重新输入
		/// </summary>
		/// <param name="enUser"></param>
		public override bool TestLogin(UserModel enUser){
            bool flag = false;
            try
            {
                base.TestLogin(enUser); 
                CreateFactory factory = new CreateFactory();
                IUser userInter = factory.CreateUser();
                if (userInter.QueryById(enUser) ==true) {
                    flag = true;
                }else{
                    throw new Exception("用户不存在,请重新输入用户名");
                }//没有检查密码是否正确的方法
            }
            catch (System.Exception)
            {
                throw new Exception("用户不存在,请重新输入用户名");
            }
            return flag;
		}
	}


public class UserExistBLL : TestUserBLL
    {
		public UserExistBLL(){

		}
		/// <summary>
		/// 检测用户是否可以登陆_用户是否存在 ,存在返回true,否则返回false。抛出异常提示:用户名不存在,请检查用户名,重新登陆
		/// </summary>
		/// <param name="enUser"></param>
		public override bool TestLogin(UserModel enUser){
            bool flag = false;
                try
            {
                base.TestLogin(enUser); 
                CreateFactory factory = new CreateFactory();//实例化工厂
                IUser userInter = factory.CreateUser();//调用实例化工厂的方法实例化一个接口
                if (userInter.QueryById(enUser) ==true)//通过ID检验用户是否存在
                {
                    flag = true;
                }
                else {
                    throw new Exception("用户不存在,请重新输入用户名");
                }
             }
            catch (System.Exception)
            {
                throw new Exception("用户不存在,请重新输入用户名");
            }
                return flag;
		}
	}

客户端调用
public bool Login(WorkModel enWork, UserModel enUser)
        {

            bool flag = false;
            UserBLL UserBLL = new UserBLL();
            LoginBLL LoginBLL = new LoginBLL();	//实例化被装饰的类
            //装饰过程
<span style="white-space:pre">	</span>    TestLoginStateBLL LoginStateBLL = new TestLoginStateBLL();
            TestLoginPWDBLL LoginPWDBLL = new TestLoginPWDBLL();
            UserExistBLL UserExistBll = new UserExistBLL();
                     
            //设置LoginStateBLL要装饰的对象
             LoginStateBLL.SetObject(LoginBLL);
           //设置UserExistBll要装饰的对象
              UserExistBll.SetObject(LoginStateBLL);
            //设置LoginPWDBLL要装饰的对象
             LoginPWDBLL.SetObject(UserExistBll);

            //检测用户是否存在
            if (LoginPWDBLL.TestLogin(enUser) == true)//在执行LoginPWDBLL的TestLogin方法时会先执行</span>

            {
                //写入工作记录
                WorkBLL WorkBll = new WorkBLL();
                if (WorkBll.InsertOnLogin(enWork) == true)
                {
                    flag = true;
                }
            }

            return flag;
        }

代码的实现相对容易,但是装饰模式需要注意的是其中的装饰顺序,通过时序图来理一下思路(只是装饰模式的时序图)。



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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值