设计模式系列漫谈之六 - 模板方法模式

在 设计模式系列漫谈之五 - 迭代器模式 中, 调用代码如下:

IListIterator iterator=new BoyList();
iterator.AddBoy(
new BoyA);
iterator.AddBoy(
new BoyB);
while (iterator.MoveNext())
{
       IBoy boy
=(IBoy)iterator.Current
       
if (boy.GetAge()<30 || boy.GetAge()>35)
       {
           iterator.RemoveBoy(boy);
       }
       
else if (boy.GetHeight()<180)
       {
           iterator.RemoveBoy(boy);
       }
       
else if (!boy.HasHouse())
       {
           iterator.RemoveBoy(boy);
       }
       
else if (!boy.HasCar())
       {
           iterator.RemoveBoy(boy);
       }
       
else if (!boy.HasMillion())
       {
           iterator.RemoveBoy(boy);
       }
       
else
       {
              Console.WriteLine(boy.Name);
       }
}


看到上面一大串IF...ELSE,相信大家一定会觉得非常不爽。这很显然是设计模式的大忌。其实我们可以通过模板方法模式来改进一下。

模板方法(Template Method)模式的解决方案
         准备一个抽象类,将部分逻辑以具体方法以及具体构造子类的形式实现,然后声明一些抽象方法来迫使子类实现剩余的逻辑。模板方法定义两个角色:
      抽象模版(AbstractClass)角色:定义了一个或多个抽象方法,具体操作由子类(具体模版)实现。然后,
定义一个模版方法,并且实现这个模版方法,其逻辑的组成步骤就是之前定义的抽象操作。抽象模板必须是一个抽象类。
      
具体模版(ConcreteClass)角色有如下的责任:实现父类所定义的一个或多个抽象方法


抽象模板如下:

namespace XiaoXue
{
    
public abstract AbstractBoy
    {
        
public string Name;
        
public abstract int GetAge();
        
public abstract int GetHeight();
        
public abstract bool HasHouse();
        
public abstract bool HasCar();
        
public abstract bool HasMillion();

        
public bool  TemplateMethod()  //抽象方法
        {
               
bool blAge=boy.GetAge()>30 && boy.GetAge()<35;
               
bool blHeight=boy.GetHeight()>180;
               
bool blHouse=boy.HasHouse();
               
bool blCar=boy.HasCar();
               
bool blMillion=boy.HasMillion();

               
return blAge && blHeight && blHouse && blCar && blMillion;
         }
    }
}

子对象具体类如下:

namespace XiaoXue
{
    
public class BoyA : AbstractBoy
    {
         
public BoyA(string name)
         {
               
base.Name=name;
         }
        
public override int GetAge()
        {
            
return 25;
        }
        
public override  int GetHeight()
        {
            
return 187;
        }
        
public override bool HasHouse()
        {
            
return true;
        }
        
public override bool HasCar()
        {
            
return false;
        }
        
public override bool HasMillion()
        {
            
return false;
        }
    }
   
public class BoyB : AbstractBoy
    {
         
public BoyB(string name)
         {
               
base.Name=name;
         }
        
public override int GetAge()
        {
            
return 32;
        }
        
public override int GetHeight()
        {
            
return 170;
        }
        
public override bool HasHouse()
        {
            
return true;
        }
        
public override bool HasCar()
        {
            
return true;
        }
        
public override bool HasMillion()
        {
            
return true;
        }
    }
}


迭代器接口和迭代器不变,请见 设计模式系列漫谈之五 - 迭代器模式

调用代码如下:

IListIterator iterator=new BoyList();
iterator.AddBoy(
new BoyA("张三"));
iterator.AddBoy(
new BoyB("李四");
while (iterator.MoveNext())
{
       AbstractBoy boy
=(AbstractBoy )iterator.Current
      
if (!boy.TemplateMethod())
       {
           iterator.RemoveBoy(boy);
       }
       
else
       {
              Console.WriteLine(boy.Name);
       }
}
posted @ 2007-12-20 20:03  李华星  阅读(450)  评论(0编辑  收藏  举报