博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
结合项目实例 回顾传统设计模式(三)装饰者模式
阅读量:6951 次
发布时间:2019-06-27

本文共 3256 字,大约阅读时间需要 10 分钟。

说到这个模式的项目实例 虫子也满头疼的 所谓装饰者模式说白了动态将职责附加到对象上。如果你在项目某个场景中需要功能扩展根据基类衍生出非常多的子类,那么装饰者模式无疑是很好的。不过其实在实际的项目中,往往大家不直接衍生子类,而是通过组合的方式,根据逻辑讲各种扩展叠加来,对外公布的只是一个标签一个壳而已。

所以这个章节,虫子就虚构一个实例了。还拿电商来说、点券赠品系统。

背景:

1.所有点券、优惠券、赠品券、积分继承同一个基类 基类券

2.不用种类的券可以混合搭配

3.积分根据不同的场景可以配置不同的规则

4.升级礼券在上层礼券基础上添加

一般情况下 大家可以就这样设计了

///
 
<summary>
    
///
 基卡
    
///
 
</summary>
    
public 
abstract 
class BaseCard
    {      
        
public 
string decription;
        
public 
abstract 
double cost();
       
    }
    
///
 
<summary>
    
///
 点卡A
    
///
 
</summary>
    
public 
class cardA : BaseCard
    {
        
public cardA()
        {
            decription = 
"
cardA
";
        }
        
public 
override 
double cost()
        {
            
return 
50.00;
        }
    }
    
///
 
<summary>
    
///
 优惠券A
    
///
 
</summary>
    
public 
class couponsA : BaseCard
    {
        
public couponsA()
        {
            decription = 
"
couponsA
";
        }
        
public 
override 
double cost()
        {
            
return 
40.00;
        }
    }
    
///
 
<summary>
    
///
 优惠券B
    
///
 
</summary>
    
public 
class couponsB : BaseCard
    {
        
public couponsB()
        {
            decription = 
"
couponsB
";
        }
        
public 
override 
double cost()
        {         
            
return 
30.00;
        }
    }
    
///
 
<summary>
    
///
 国庆礼券
    
///
 
</summary>
    
public 
class GQCard : BaseCard
    {
        cardA a = 
new cardA();
        couponsA ca = 
new couponsA();
        
public GQCard()
        {
            decription = 
"
GQCard
";
        }
        
public 
override 
double cost()
        {
            
return a.cost() + ca.cost();
        }
    }
    
///
 
<summary>
    
///
 国庆升级A等礼券
    
///
 
</summary>
    
public 
class GQACard : BaseCard
    {
        cardA a = 
new cardA();
        couponsA ca = 
new couponsA();
        couponsB cb = 
new couponsB();
        
public GQACard()
        {
            decription = 
"
GQACard
";
        }
        
public 
override 
double cost()
        {
            
return a.cost() +ca.cost()+ cb.cost();
        }
    }

 

设计模式的原则是类应该对扩展开放对修改关闭,而上述设计在礼券升级种类越来越多的情况下并且现有的礼券已经频繁更新的话 对于庞大的礼券系统肯定是不理想的

那么我们换个思路

 

///
 
<summary>
    
///
 基卡
    
///
 
</summary>
    
public 
abstract 
class BaseCard
    {      
        
public 
string decription;
        
public 
abstract 
double cost();
       
    }
    
///
 
<summary>
    
///
 点卡A
    
///
 
</summary>
    
public 
class cardA : baseoupons
    {
        BaseCard basec;
        
public cardA(BaseCard basec)
        {
            
this.basec = basec;
            decription = 
"
cardA,
" + basec.decription;
        }
        
public 
override 
double cost()
        {
            
return 
50.00 + basec.cost(); 
        }
    }
    
///
 
<summary>
    
///
 优惠券A
    
///
 
</summary>
    
public 
class couponsA : baseoupons
    {
        BaseCard basec;
        
public couponsA(BaseCard basec)
        {
            
this.basec = basec;
            decription = 
"
couponsA,
" + basec.decription;
        }
        
public 
override 
double cost()
        {
            
return 
40.00 + basec.cost();
        }
    }
    
///
 
<summary>
    
///
 优惠券B
    
///
 
</summary>
    
public 
class couponsB : baseoupons
    {
        BaseCard basec;
        
public couponsB(BaseCard basec)
        {
            
this.basec = basec;
            decription = 
"
couponsB,
" + basec.decription;
        }
        
public 
override 
double cost()
        {
            
return 
30.00 + basec.cost(); 
        }
    }
    
///
 
<summary>
    
///
 基类礼券
    
///
 
</summary>
    
public 
class baseoupons : BaseCard
    {
        BaseCard basec;
        
public baseoupons(BaseCard basec)
        {
            
this.basec = basec;
            decription = basec.decription;
        }
        
public baseoupons()
        {
            
        }
        
public 
override 
double cost()
        {
            
if (basec != 
null)
            {
                
return basec.cost();
            }
            
else
            {
                
return 
0;
            }
        }
      
    }

 

 让我们看看装饰者模式的强大

 

  BaseCard a = 
new baseoupons();
            a = 
new cardA(a);
            a = 
new couponsA(a);
            a = 
new couponsB(a);
            Console.WriteLine(
"
国庆礼券由
"+a.decription+
"
组成
");
            Console.WriteLine(a.cost().ToString());
            BaseCard b = 
new cardA(a);
           
            Console.WriteLine(
"
国庆升级礼券由
" + b.decription + 
"
组成
");
            Console.WriteLine(b.cost().ToString());
            Console.ReadLine();

 

总结:继承属于扩展形式之一,但不见得是达到弹性设计的最佳方式,在我们的设计当中应该允许行为可以被扩展,而无需修改现有的代码。就如上述的例子装饰者模式也可以让我们扩展行为。不过装饰者模式也有缺点,它会导致设计中出现许多小对象,如果过度使用,会让程序变得很复杂。

 

转载于:https://www.cnblogs.com/dubing/archive/2011/10/02/2198011.html

你可能感兴趣的文章
首席DBA用SQL洪荒之力,造一把通向数据库的钥匙
查看>>
myEclipse中配置maven
查看>>
SOAP webserivce 和 RESTful webservice 对比及区别
查看>>
OC第一天——面向对象
查看>>
.NET中的六个重要概念:栈、堆、值类型、引用类型、装箱和拆箱
查看>>
Redis的Pub/Sub模式
查看>>
Maven中&amp;lt;dependencies&amp;gt;节点和&amp;lt;dependencyManagement&amp;gt;节点的区别
查看>>
.NET中异常处理的最佳实践(译)
查看>>
vim编辑器使用
查看>>
Hibernate4.3在开发中的一些异常总结(持续更新)
查看>>
DedeCMS中用到的字符编码转换1
查看>>
AngularJS 服务 demo
查看>>
DockerCon 2016 深度解读: Docker安全
查看>>
iOS集合视图单元格高亮和选中的区别
查看>>
Mysql增量备份之Mysqldump & Mylvmbackup
查看>>
SpriteBuilder复杂CCB在App场景加载时报错排查
查看>>
文章用手,产品用心
查看>>
Reveal App试用时间破解
查看>>
线性空间(向量空间)
查看>>
多媒体之录音
查看>>