Visitor 观察者模式

本文介绍了一种设计模式——观察者模式,它将类结构与操作分离,允许在不修改类结构的情况下自由操作类中的元素。文章通过一个汽车类结构的例子详细展示了如何实现观察者模式,并解释了其工作原理。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

模式定义

 

观察者模式将类的结构与操作于该类上的算法分离开,使得模式的使用者能在不改变类结构的前提下自由地对类中的元素进行不同的操作。

使用方法

 


Visitor将自己注册到类对象中,由类对象通过回调的方式来启动观察者访问操作类内部的数据元素或结构。

使用范围

 

  • 类结构内部包含很多具有不同接口的类对象,需要定义针对于具体类的操作
  • 需要对于类结构中的类对象定义不同的操作
  • 需要重新定义或扩展对类结构中的类对象的操作

举例说明

 

假设定义一个汽车的复杂的类结构Car以及Car的组件Engine, Wheel,均作为CarElement的元素存在。

public interface CarElement {
	void accept(CarElementVisitor visitor);
}

--------
public class Wheel implements CarElement{
	private String name;
	Wheel(String name){
		this.name = name;
	}
	public String getName(){
		return name;
	}
	public void accept(CarElementVisitor visitor) {
		visitor.visit(this);
	}

}
--------
public class Engine implements CarElement{

	public void accept(CarElementVisitor visitor) {
		visitor.visit(this);
	}

}


--------
public class Car implements CarElement{
	CarElement[] elements;
	public CarElement[] getElements(){
		return elements.clone();
		
	}
	public void accept(CarElementVisitor visitor) {
		visitor.visit(this);
	}
	
	Car(){
		this.elements = new CarElement[]{
				new Engine(), 
				new Wheel("front two wheels"), 
				new Wheel("back two wheels")
		};
	}

}

每个CarElement的实现类均通过accept()的方法来回调visitor并访问自身。

接下来即可定义一个visitor类,比如Driver。为了使得visitor具有可扩展可延续性,可以将Driver抽象出一个接口来,之后可以根据不同的需求来定义不同的Driver。观察Driver类是如何将自己作为参数注入Car类结构的。

interface CarElementVisitor {
    void visit(Wheel wheel);
    void visit(Engine engine);
    void visit(Car car);
}

--------
public class Driver implements CarElementVisitor{

	public void visit(Wheel wheel) {
		System.out.println("Rolling " + wheel.getName());		
	}

	public void visit(Engine engine) {
		System.out.println("Starting engine");
	}

	public void visit(Car car) {
		System.out.println("I am driving");
		for (CarElement ele:car.getElements()){
			ele.accept(this);
		}		
		System.out.println("going...");
	}

}

最后用一个具体的调用过程来实现visitor。

public class CarVisitorClient {
	public static void main(String args[]){
		Car car = new Car();
		car.accept(new Driver());
	}
}

下载示例

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值