一、 访问者模式简介
1. 什么是访问者模式
访问者模式(Visitor Pattern) 属于行为型设计模式的一种,是一种相对简单的设计模式。其定义如下:Represent an operation to be performed on the elements of an object structure .Visitor lets you define a new operation without changing the classes of the elements on which it operates .(封装一些作用于某种数据结构中的各元素操作,它可以在不改变数据结构的前提下定义作用于这些元素的新的操作)。 简单来说访问者模式就是通过提供一个访问类,它改变了元素类的执行算法,通过这种方式元素的执行算法可以随着访问者改变而改变。
2. 使用场景
作为一个苦逼的打工人,每天都要坐着清晨的2路公交车上班。很多小伙伴可能也和博主一样注意到了,在公交打卡的时候,不同的卡种收费是不同的,比如普通人直接打卡可能要收费2元,学生卡1元而老年卡则是免费这种。那么今天我们就通过模拟一个简单的公交卡系统来讲述访问者模式,请大家系好安全带,准备发车了~
二、访问者模式的实现
1. 设计思路
首先我们要分析一下在公交打卡这个业务里,存在多少个角色参与:
- 公交卡抽象类(Element): 首先不管是学生卡还是老年卡,其本质都属于公家卡的一种,因此我们可以通过抽离一个公交卡的抽象类来定义他们的共同行为。
- 不同公交卡的实现类(ConcreteElement):根据不同的卡种定义不同的属性。
- 打卡器算法抽象接口(Visitor):由于公交车也存在很多种,每种公交车的打卡规则可能不同,因此需要将其共有行为做抽离。
- 打卡器实现类(ConcreteVisitor):具体的打卡算法实现。
那么我们根据我们的分析来画一个简单的类图:
ok,接下来我们只需要看图写代码即可。
2. 代码实现
第一步: 创建visitor接口及实现类
public interface Visitor {
void visit(SimpleCard simpleCard);
void visit(StudentCard studentCard);
void visit(OldCard oldCard);
}
public class BusVisitor implements Visitor{
@Override
public void visit(SimpleCard simpleCard) {
System.out.println("滴滴~普通卡,扣费2元");
}
@Override
public void visit(StudentCard studentCard) {
System.out.println("滴滴~学生卡,扣费1元");
}
@Override
public void visit(OldCard oldCard) {
System.out.println("滴滴~老年卡,免费");
}
}
第二步: 创建card抽象类及实现类
public abstract class Card {
protected Long amt;
abstract void accept(Visitor visitor);
public Card(Long amt) {
super();
this.amt = amt;
}
}
public class SimpleCard extends Card{
@Override
void accept(Visitor visitor) {
visitor.visit(this);
}
public SimpleCard(Long amt) {
super(amt);
}
}
public class StudentCard extends Card{
@Override
void accept(Visitor visitor) {
visitor.visit(this);
}
public StudentCard(Long amt) {
super(amt);
}
}
public class OldCard extends Card{
@Override
void accept(Visitor visitor) {
visitor.visit(this);
}
public OldCard(Long amt) {
super(amt);
}
}
第三步:创建客户端调用
public class Client {
public static void main(String[] args) {
Visitor busVisitor = new BusVisitor();
OldCard oldCard = new OldCard(100l);
StudentCard studentCard = new StudentCard(200l);
SimpleCard simpleCard = new SimpleCard(500l);
oldCard.accept(busVisitor);
studentCard.accept(busVisitor);
simpleCard.accept(busVisitor);
}
}
测试结果:
到这里一个简单的公交系统就完成,有疑问或者改进意见的同学欢迎评论区留言~
三、访问者模式总结
1. 访问者模式的特点
优点:
- 符合单一职责原则
- 具有优秀的拓展性
- 灵活性非常高
缺点:
- 具体元素对访问者公布细节
- 具体元素拓展性差
- 违背了依赖倒置原则
2. 访问者模式的使用场景
- 对象结构中的对象对应的类很少变化但经常需要在此对象结构上定义新的操作。
- 需要对一个对象结构中的对象进行很多并且不相关的操作,同时开发者想要避免这些操作污染对象类。
四、结语
今天的代理模式讲解就全部结束了,设计模式的相关代码已经在gitee上收录,有需求的小伙伴可以直接拿走:
有疑问的小伙伴欢迎评论区留言或者私信博主,博主会在第一时间为你解答。
码字不易,感到有收获的小伙伴记得要关注博主一键三连,不要当白嫖怪哦~
博主在这里祝大家可以在新的一年升职加薪,走上人生巅峰!