实际项目中简单工厂及委托的继承的使用

    最近在重构公司的电子商务网站,其中有个打折消费的功能.这里简单介绍下,比如,网站搞活动买二送一(以下称A),或者买二瓶其中价格低的一瓶半价(以下称B),.
    最初的设计是很粗糙的,因为之前网站是没有活动,后来增加一个活动,现在又要增加新的活动.从一开始的直接写代码,到后来的if else 判断打折条件,到现在又要添加新的打折,觉得这样的代码写的很粗糙,有种不爽的感觉.
    现在刚好有机会重构这里,就大概设计一下,也好让这里更面向对象一点.之前没有这样设计是因为根本没有想到会有这么多的改变,呵呵,还好可以重构,这个也是不断学习的过程.
    好了,废话不说了,贴下设计类图.
         
    之前有考虑使用接口,因为促销A和促销B,都要实现方法OperateShippingCart,但是后来一想,这2次促销方式,其实都可以统称促销方式,也就是说他们是"is-a"的关系,这样的话使用抽象类比较好.定义一个抽象类Sales,促销A和促销B继承他,并重写他的促销方法.
    然后使用简单工厂方法,根据不同的要求创建不同的实例,这样也使用了多态的特性.

                Sales sale  =  SaleFactory.CreateSale();
                
if  (sale  !=   null ) // 如果有促销活动
                 {
                    sale.Operate 
+= AddPresent;//这里使用了委托
                    save = sale.CountShoppingCart(list);

                }


    这样就抛弃了起初很多if..else..判断不同的促销方式了,要新增加促销方式的话,使其直接继承Sale,然后重写OperateShippingCart就可以了.

    下面说下,这里我使用了委托.使用委托是因为,促销方式A和B的功能只是计算打折后的价格,但是要操作购物车,比如购物满2瓶,就要再赠送他1瓶,或者购物满500元,也要送一瓶酒.这里就需要直接操作购物车了.这里我的促销方式是放在另外一个工程里的,并在website里引用了它,当然不能在OperateShippingCart里直接操作购物车,这样就要引用website导致循环引用了.
    后来想了下,这个还是使用委托的好.
    委托是对函数签名的封装,事件是委托的一种特殊形式.
    要使用委托,首先要定义委托,然后定义事件,在class中判断事件如果不为空,则调用事件订阅者的方法.当然要操作购物车是需要传递参数的,给委托传递参数,只要让参数继承自EventArgs就可以了,这里还遇到个问题,就是Sale里定义了委托,但是在子类中并不能调用它,会出现错误,后来百度知,需要在父类中定义一个虚方法调用委托,然后在子类中重写并调用这个方法就搞定了.

public   class  ShoppingCartEventArgs :EventArgs
    
{
        
int prodID;

        
public int ProdID
        
{
            
get return prodID; }
            
set { prodID = value; }
        }

        
int type;

        
public int Type
        
{
            
get return type; }
            
set { type = value; }
        }

        
int quantity;

        
public int Quantity
        
{
            
get return quantity; }
            
set { quantity = value; }
        }

    }

 

public   abstract   class  Sales
    
{
        
public delegate void OperatShoppingCartEventHandle(object sender, ShoppingCartEventArgs args);

        
public event OperatShoppingCartEventHandle Operate;

        
/**//// <summary>
        
/// 对购物车中的产品进行折扣处理
        
/// </summary>
        
/// <param name="list"></param>
        
/// <returns>返回节省下来的金额</returns>

        public abstract decimal CountShoppingCart(List<CShoppingCartItem> list);

        
/**//// <summary>
        
/// 调用委托
        
/// </summary>
        
/// <param name="sender"></param>
        
/// <param name="args"></param>

        public virtual void Event(object sender, ShoppingCartEventArgs args)
        
{
            
if (Operate != null)
            
{
                Operate(sender, args);
            }


        }


  public   class  MNSale : Sales
    
{       
        
ISale 成员 同样的一瓶买几送几#region ISale 成员 同样的一瓶买几送几

        
public override decimal CountShoppingCart(List<CShoppingCartItem> list)
        
{
            
decimal save = 0;//节省多少钱
            try
            
{
                
int count = 0;//总有多少瓶

                
//除掉不是活动的酒
                foreach (CShoppingCartItem item in list)
                
{
                    
if (item.Sale != (int)ProductState.活动酒)
                    
{
                        list.Remove(item);
                    }

                }


                
//循环活动产品
                foreach (CShoppingCartItem item in list)
                
{
                    count 
= item.Quantity;
                    PromotionSend promotionSend 
= PromotionSendService.GetPromotionSendByWhereClip(PromotionSend._.BeginTime <= DateTime.Now && PromotionSend._.EndTime >= DateTime.Now && PromotionSend._.Buy <= count);
                    
if (promotionSend != null)
                    
{
                        
int m = count / promotionSend.Buy;//买2送1
                        save += m * item.MemberPrice;
                        
//if (Operate != null)//因为委托在父类定义,这里不能判断是否为空,所以不论是否为空只要先把要传递的参数定义好了再说
                        
//{
                            ShoppingCartEventArgs e=new ShoppingCartEventArgs();
                            e.ProdID 
= int.Parse(item.ProductID.Substring(1));
                            e.Quantity 
= m;
                            e.Type 
= 0;
                            Event(
this, e);
                        
//}
                    }

                }


            }

            
catch { }

            
return save;
        }



        
public override void Event(object sender, ShoppingCartEventArgs args)
        
{
            
base.Event(sender, args);
        }

        
#endregion


这里不得不佩服下园子里那些强人,能把文章写的很长很详细而且面面俱到,真是让人学习的楷模.而自己写的文章总觉得拖泥带水,一带而过,呵呵
还要再学习啊,大家共勉

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值