最爱Java

书山有路勤为径,学海无涯苦作舟

《AspectJ Cookbook》读书笔记十七: 实现创建型面向对象设计模式

一.实现单件模式
        单件模式允许把类定义成具有应用程序内的一个运行时实例。通常,通过不给特定类提供默认构造函数来实现单件。
package com.aspectj;

import java.util.Hashtable;

public abstract aspect SingletonPattern issingleton(){
    
private Hashtable singletons = new Hashtable();
    
    
public interface Singleton{}
    
    
public interface NonSingleton{}
    
    
//Pointcut to define specify an interest in all creations
    
//of all Classes that extend Singleton
    pointcut selectSingletons() : call((Singleton+).new(..));
    
    
//Pointcut to ensure that any classes in the Singleton inheritance tree
    
//that are marked as Non Singletons are not included in the Singleton
    
//logic.
    pointcut excludeNonSingletons():!call((NonSingleton+).new (..));
    
    Object around() : selectSingletons()
&&excludeNonSingletons() {
        Class singleton 
= thisJoinPoint.getSignature().getDeclaringType();
        
synchronized(singletons) {
            
if (singletons.get(singleton) == null{
                singletons.put(singleton, proceed());
            }

        }

        
return (Object) singletons.get(singleton);
    }

}


        SingletonPattern抽象方面定义了两个角色:Singleton和NonSingleton。这些角色被实现为接口,使得抽象方面可以处理单件,而无需关注实现细节。
        Singleton接口由SingletonPattern抽象方面的子方面应用于目标应用程序内将被视作单件的任何类。类似地,NonSingleton接口被应用于可能通过继承从其父类获得单件行为的类。如果决定子类不是一个单件,那么就可以使用NonSingleton接口,使得重写父类的单件特征。
        声明两个切入点来捕获何时实例化具有Singleton接口的类。selectSingletons()切入点定义用于选择对扩展Singleton接口的类上构造函数的调用。为了支持单件子类的关闭单件行为的要求,声明了excludeNonSingletons()切入点。当需要阻止超类的单件行为影响子类时,可以通过单定的方面重写这个切入点。
        around()通知用于捕获对应用于Singleton接口的类上构造函数的调用。around()通知会重写构造函数,以检查尚未创建正在实例化的对象的类型。
        使用thisJoinPoint变量提供的类的信息,在单件散列表上查询正在创建的对象的类。如果类的类型在散列表中不存在,那么就添加它的类,并通过调用proceed()来构造那个类的一个对象,这会执行原始的构造函数逻辑。process()调用会返回构造的对象,并把这个对象与类对象一起添加到散列表中。
        如果散列表中存在类的类型,那么就不需要创建新对象。依据它的类从散列表映射检索单件对象,并作为构造函数调用的结果从around()通知返回这个对象。
        以下为如何把SingletonPattern抽象方面应用于特定的应用程序中。
package com.aspectj;

public aspect PrinterSingleton extends SingletonPattern {
    declare parents:Printer 
implements Singleton;
    declare parents:SpecializedPrinter 
implements NonSingleton;
}


二.实现原型模式
        原型模式支持基于原始对象创建复制的对象。
package com.aspectj;

public abstract aspect PrototypePattern {
    
protected interface Prototype{}
    
    
public Object Prototype.clone() throws CloneNotSupportedException {
        
return super.clone();
    }

    
    
public Object cloneObject(Prototype object) {
        
try {
            
return object.clone();
        }
 catch (CloneNotSupportedException ex) {
            
return createCloneFor(object);
        }

    }

    
    
protected Object createCloneFor(Prototype object) {
        
return null;
    }

}


    clone()方法是用于实现对象深复制的Java机制。有些基类可能不支持被复制;createCloneFor(Prototype)方法,可以被子方面重新,以执行通用方面不知道的特定复制操作。
package com.aspectj;

public aspect GraphicPrototypes extends PrototypePattern {
    declare parents:MyClass 
implements Prototype;

    declare parents:AnotherClass 
implements Prototype;

    
//declare parents:Staff implements Prototype;

    
protected Object createCloneFor(Prototype object) {
        
if (object instanceof MyClass) {
            
return  null;
        }
 else if (object instanceof AnotherClass) {
            
return null;
        }
 else {
            
return null;
        }

    }

}


三.实现抽象工厂模式
    抽象工厂模式支持对一组相关类进行实例化,同时把工厂模式的客户与准确的实现隔离开。
package com.aspectj;

public interface ComputerFactory {
    
public Computer createPentiumProcessorComputer();
    
    
public Computer createPentiumProcessorComputerWithHardDisk(HardDisk hardDisk);
}


package com.aspectj;

public aspect DefaultComputerFactoryImplementation {
    
    
public Computer createPentiumProcessorComputer() {
        Processor processor 
= new Processor("Pentium 4:9089085043");
        Motherboard motherboard 
= new Motherboard("019283" , processor);
        HardDisk hardDisk 
= new HardDisk("739874");
        FloppyDisk floppyDisk 
= new FloppyDisk("93746");
        Computer computer 
= new Computer("12345" , motherboard,hardDisk,floppyDisk);
        
return computer;
    }

    
    
public Computer createPentiumProcessorComputerWithHardDisk(HardDisk hardDisk) {
        Processor processor 
= new Processor("Pentium Standard:123478");
        Motherboard motherboard 
= new Motherboard("434244" , processor);
        FloppyDisk floppyDisk 
= new FloppyDisk("434234");
        Computer computer 
= new Computer("56789" , motherboard,hardDisk,floppyDisk);
        
return computer;        
    }

    
}


四.实现工厂方法模式
package com.aspectj;

public aspect DefaultComputerCreatorImplementation {
    
public void ComputerCreator.createComputerAndPrintInventory(String serial) {
        System.out.println(
"Inventory of computerparts:");
        System.out.println(
this.createComputer(serial).toString());
    }

}


package com.aspectj;

public aspect DefaultComputerCreatorImplementation {
    
public void ComputerCreator.createComputerAndPrintInventory(String serial) {
        System.out.println(
"Inventory of computerparts:");
        System.out.println(
this.createComputer(serial).toString());
    }

}

五.实现生成器模式
        生成器模式用于捕获在创建对象时可能需要的复杂步骤。这些步骤被实现为生成器类上的方法;在完成每个必须的步骤之后,就可以调用生成器来创建所得到的生成对象。
package com.aspectj;

public interface TextPhraseBuilder {
    
public void buildHeader(String title);
    
    
public void buildContent(String content);
    
    
public void buildFooter(String closingContent);
    
    
public String getResult();
}

 

package com.aspectj;

public aspect TextPhraseBuilderDefaultImplementation {
    
public StringBuffer TextPhraseBuilder.result = new StringBuffer();
    
    
public String TextPhraseBuilder.getResult() {
        
return result.toString();
    }

    
    
/**
     * Declares a compiler error that gets reported if other classes
     * (except Builders or this aspect) try to access the result variable.
     
*/

    declare error:(
            set(
public StringBuffer TextPhraseBuilder +.result)
            
|| get(public StringBuffer TextPhraseBuilder +.result))
            
&& !(within(TextPhraseBuilder +)
            
|| within(TextPhraseBuilderDefaultImplementation)) :
                
"variable result is aspect protected. use getResult() to access it";
}

posted on 2008-08-27 11:00 Brian 阅读(1117) 评论(0)  编辑  收藏 所属分类: 《AspectJ Cookbook》读书笔记


只有注册用户登录后才能发表评论。


网站导航:
 

公告


导航

<2008年8月>
272829303112
3456789
10111213141516
17181920212223
24252627282930
31123456

统计

常用链接

留言簿(4)

随笔分类

随笔档案

收藏夹

搜索

最新评论

阅读排行榜

评论排行榜