首页 > 代码库 > 设计模式—访问者模式

设计模式—访问者模式

访问者模式:表示一个作用于某对象结构中的各个元素操作。可以在不改变元素类的前提下为这种对象添加新操作

  优势:很容易扩展对象的功能,不需要再对对象就行修改操作,只需要添加一个功能扩展类即可。

  劣势:数据结构中存储的对象类型需要唯一,不允许有两种及以上类型    

示例说明:为企业和个人客户增加数据分析请求功能(新操作)。

结构类图:

技术分享

先定义一个Customer 抽象类,添加accept抽象方法。

package com.zpj.designMode.Visitor;/** * @author PerKins Zhu * @date:2016年9月25日 上午7:10:53 * @version :1.1 *  */public abstract class Customer {    private String type;    public String getType() {        return type;    }    public void setType(String type) {        this.type = type;    }    public abstract void accept(Visitor vistor);}

 

添加个人PersonCustomer 

和企业客户 EnterpriseCustomer 

package com.zpj.designMode.Visitor;/** * @author PerKins Zhu * @date:2016年9月25日 上午7:12:08 * @version :1.1 *  */public class PersonCustomer extends Customer {    @Override    public void accept(Visitor vistor) {        vistor.visitPersonCustomer(this);    }}package com.zpj.designMode.Visitor;/** * @author PerKins Zhu * @date:2016年9月25日 上午7:13:57 * @version :1.1 *  */public class EnterpriseCustomer extends Customer {    @Override    public void accept(Visitor vistor) {        vistor.visitEnterpriseCustomer(this);    }}

 

添加访问者抽象类Visitor ,这里也可以定义一个接口。

package com.zpj.designMode.Visitor;/** * @author PerKins Zhu * @date:2016年9月25日 上午7:06:42 * @version :1.1 *  */public abstract class Visitor {    public abstract void visitPersonCustomer(PersonCustomer personCustomer);    public abstract void visitEnterpriseCustomer(EnterpriseCustomer enterpriseCustomer);}

 

添加两个功能扩展子类:

  服务请求ServiceRequestVisitor

   数据分析请求PredilectionAnalyzeVisitor 

package com.zpj.designMode.Visitor;/** * @author PerKins Zhu * @date:2016年9月25日 上午7:16:47 * @version :1.1 *  */public class ServiceRequestVisitor extends Visitor {    @Override    public void visitPersonCustomer(PersonCustomer personCustomer) {        System.out.println(personCustomer.getType() + "提出服务请求!");    }    @Override    public void visitEnterpriseCustomer(EnterpriseCustomer enterpriseCustomer) {        System.out.println(enterpriseCustomer.getType() + "提出服务请求!");    }}package com.zpj.designMode.Visitor;/** * @author PerKins Zhu * @date:2016年9月25日 上午7:22:48 * @version :1.1 *  */public class PredilectionAnalyzeVisitor extends Visitor {    @Override    public void visitPersonCustomer(PersonCustomer personCustomer) {        System.out.println(personCustomer.getType() + "提出数据分析请求!");    }    @Override    public void visitEnterpriseCustomer(EnterpriseCustomer enterpriseCustomer) {        System.out.println(enterpriseCustomer.getType() + "提出数据分析请求!");    }}

 

既然是对某个数据结构中的对象进行操作,肯定要添加一个数据结构

package com.zpj.designMode.Visitor;import java.util.ArrayList;import java.util.List;/** * @author PerKins Zhu * @date:2016年9月25日 上午7:24:23 * @version :1.1 *  */public class ObjectStructure {    private List<Customer> customers = new ArrayList<Customer>();    public void add(Customer cus) {        customers.add(cus);    }    public void request(Visitor vis) {        for (Customer cus : customers) {            cus.accept(vis);        }    }}

 

跑一下看看

package com.zpj.designMode.Visitor;import org.junit.Test;/** * @author PerKins Zhu * @date:2016年9月25日 上午7:27:44 * @version :1.1 *  */public class Client {    @Test    public void test01(){        ObjectStructure obj = new ObjectStructure();                Customer cu01 = new PersonCustomer();        cu01.setType("个人用户");                Customer cu02 = new EnterpriseCustomer();        cu02.setType("企业用户");                obj.add(cu01);        obj.add(cu02);                ServiceRequestVisitor vis = new ServiceRequestVisitor();        obj.request(vis);                PredilectionAnalyzeVisitor vis02 = new PredilectionAnalyzeVisitor();        obj.request(vis02);    }    }

 

运行结果:

  个人用户提出服务请求!

  企业用户提出服务请求!
  个人用户提出数据分析请求!
  企业用户提出数据分析请求!

如果需要添加Customer的功能,不需要对Customer及其实现类进行修改,只需添加一个Visitor的实现类即可,在实现类中添加Customer的新功能。

-----------------------------

设计模式—访问者模式