zoukankan      html  css  js  c++  java
  • Java设计模式之观察者模式

    Java设计模式之观察者模式

    一直想写一篇学习观察者模式的总结没有契机,今天学习阻塞队列的原理时候看到在实现生产者消费者的时候用到了通知模式,就是所谓的观察者模式,正好顺便整理一下。

    1. 简介

    观察者模式定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新。也就是 发布-订阅 的模式。

    观察者模式涉及到的参与者有:

    • Subject(目标):被观察者的接口,提供注册/删除观察者和发通知的方法;
    • Observer(观察者):观察目标的对象接口,提供目标发生改变时需要处理更新的方法;
    • ConcreteSubject(具体目标):实现被观察者接口的具体被观察者类,维护一个观察者的引用,在发通知的时候调用观察者的更新方法;
    • ConcreteObserver(具体观察者):实现观察者接口的具体观察者类。

    观察者模式的使用场景

    • 比如你微博关注了一个人,那么这个人发布的微博就会推送到你这。
    • 还比如你关注了一个微信公众号,这个公众号发布的文章也会推送到你这。

    2. 实例代码

    就拿微博关注来举个例子,一些人关注了一个大V,那么大V每次发微博,这些人就会收到推送,哪天大V发的微博让某些人不爽了,果断取关,那么以后就不会收到大V的推送消息了。

    新建Subject接口

    package con.wangjun.designPattern.observer;
    
    public interface Subject {
    	public void addFans(Observer o);  // 添加粉丝
    	public void removeFans(Observer o);  // 移除粉丝
    	public void notifyFans(String str);  // 通知粉丝
    }
    

    新建Observer接口

    package con.wangjun.designPattern.observer;
    
    public interface Observer {
    	// 当被观察者调用notifyFans发通知,update方法会被回调
    	public void update(String str);
    }
    

    新建Subject实现类

    package con.wangjun.designPattern.observer;
    
    import java.util.ArrayList;
    import java.util.List;
    
    public class VSubject implements Subject {
    	
    	List<Observer> list = new ArrayList<>();
    	
    	// 发布微博
    	public void publish(String str) {
    		System.out.println("大V发布微博:" + str);
    		// 通知所有粉丝
    		notifyFans(str);
    	}
    
    	@Override
    	public void addFans(Observer o) {
    		list.add(o);
    	}
    
    	@Override
    	public void removeFans(Observer o) {
    		list.remove(o);
    	}
    
    	@Override
    	public void notifyFans(String str) {
    		for(int i = 0; i < list.size(); i++) {
    			list.get(i).update(str);
    		}
    	}
    
    }
    

    新建Observer实现类

    package con.wangjun.designPattern.observer;
    
    public class FansObserver implements Observer {
    	
    	private String name;
    	
    	public FansObserver(String name) {
    		this.name = name;
    	}
    
    	@Override
    	public void update(String str) {
    		System.out.println(name + " 收到大V的微博发文:" + str);
    	}
    
    }
    

    新建测试类

    package con.wangjun.designPattern.observer;
    
    import java.util.ArrayList;
    import java.util.List;
    
    public class Main {
    
    	public static void main(String[] args) {
    		VSubject vs = new VSubject();  // 大V的实例  
    		List<FansObserver> fans = new ArrayList<>();  //存储所有粉丝
    		
    		for(int i = 0; i < 5; i++) {
    			FansObserver f = new FansObserver("name" + (i + 1));
    			fans.add(f);
    			vs.addFans(f);
    		}
    		// 本次发微博,5个粉丝都收到推送
    		vs.publish("我的女朋友真好看!");
    		// 居然秀恩爱,前2个粉丝,看不下去了,取关!
    		for(int i = 0; i < 2; i++) {
    			vs.removeFans(fans.get(i));
    		}
    		
    		//这次发微博,那两个取关的人就看不到了
    		vs.publish("我要送所有粉丝一部iPhone X");
    	}
    }
    

    运行结果

    大V发布微博:我的女朋友真好看!
    name1 收到大V的微博发文:我的女朋友真好看!
    name2 收到大V的微博发文:我的女朋友真好看!
    name3 收到大V的微博发文:我的女朋友真好看!
    name4 收到大V的微博发文:我的女朋友真好看!
    name5 收到大V的微博发文:我的女朋友真好看!
    大V发布微博:我要送所有粉丝一部iPhone X
    name3 收到大V的微博发文:我要送所有粉丝一部iPhone X
    name4 收到大V的微博发文:我要送所有粉丝一部iPhone X
    name5 收到大V的微博发文:我要送所有粉丝一部iPhone X
    

    参考:

    《面向对象的设计模式》

    JAVA设计模式之观察者模式https://www.cnblogs.com/luohanguo/p/7825656.html

  • 相关阅读:
    Asp.net弹出浏览器客户端确认对话框代码 Carlwave
    VS 2005 与SQL Server 2005整合优势在哪里?(from csdn.net) Carlwave
    如何让搜索引擎收录我的站点 Carlwave
    超强扩展性的DNNDotNetNuke模块功能分类列表(from 中国DNN) Carlwave
    DotNetNuke命名空间概述 Carlwave
    Most Popular Questions and Answers on ASP.NET Whidbey(from asp.net forums,write by ASP.NET Team) Carlwave
    火箭官方宣告麦蒂缺阵五周 季后赛前景蒙上阴影 Carlwave
    asp.net有效使用缓存(转) Carlwave
    《Business Rules Engine Overview》《业务规则引擎概述》write by Mark Kamoski Carlwave
    中国详细省市县自治区名称列表(含access数据库和sql2000备份数据库) Carlwave
  • 原文地址:https://www.cnblogs.com/scuwangjun/p/9127398.html
Copyright © 2011-2022 走看看