观察者模式:设计模式系列(七)

  观察者模式(Observer Pattern):是一种由多同本质对象与另一种目标对象构建而成,当目标对象发生改变时,多种同本质对象会被通知及作出一系列动作的设计模式,归类为行为型模式。

  这一模式的解读分为以下几个方面:

  • 有很多实例对象具有同一种目的,所以可以从中抽象出相关的本质。
  • 目标对象不定时会发生变化,并且对象数量不唯一,所以也可以从中抽象出相关的本质。
  • 只要目标对象一变化,关注它的很多对象会执行相关的方法。

  使用观察者模式的思考过程如下:

  1. 有一些实例对象对于程序运行方式是关键,如果它有变化,那么处理的算法就需要跟着变化。
  2. 需要时刻盯着这些会不定时变化的关键实例对象,防止处理方式不对导致产生问题。
  3. 这些关键实例对象一变化就要告诉别人我有变化,而盯着变化的人则要。

  那么再明确一下结构,观察者模式结构包含观察者实现类、观察者抽象出来的接口或协议、目标实现类、目标抽象出来的接口或协议。

观察者模式示例代码如下(Swift语言):

protocol ObjectBluePrint{
 
    func registerObserver(observer:ObserverBluePrint);
    func unregisterObserver(observer:ObserverBluePrint);
    func change();
    func notify();
}

class Object:ObjectBluePrint{
    
    private var observer = [ObserverBluePrint]();
    
    func registerObserver(observer:ObserverBluePrint) {
        self.observer.append(observer);
        print("Registering Observer... count:\(self.observer.count)");
    }
    
    func unregisterObserver(observer: ObserverBluePrint) {
        for(var i = 0;i < self.observer.count;i++){
            if(self.observer[i].getObserverID() == observer.getObserverID()){
                self.observer.removeAtIndex(i);
            }
        }
        print("Unregistering Observer... count:\(self.observer.count)");
    }
    
    func change() {
        print("I am Object,and I have already done something");
        self.notify();
    }
    
    func notify() {
        print("Now I am going to notify Observer");
        for(var i = 0;i < self.observer.count;i++){
            
            observer[i].update();
        }
    }
}

protocol ObserverBluePrint{
    
    func getObserverID()->Int;
    func setObserverID(id:Int);
    func update();
    func show();
}

class Observer:ObserverBluePrint{
    
    var id:Int?;
    
    func getObserverID()->Int {
        return self.id!;
    }
    
    func setObserverID(id:Int) {
        self.id = id;
    }
    
    func update(){
        print("I am Observer \(self.id!),I have been notified");
        self.show();
    }
    
    func show(){
        print("Observer \(self.id!) can do something for the changed of Object");
    }
}

var object:ObjectBluePrint = Object();

var observer1:ObserverBluePrint = Observer();
observer1.setObserverID(1);
object.registerObserver(observer1);
var observer2:ObserverBluePrint = Observer();
observer2.setObserverID(2);
object.registerObserver(observer2);

object.change();

object.unregisterObserver(observer1);

object.change();

  代码分析:这段示例代码写得有点复杂,主要是为了突出这个模式的特点。首先创建ObjectBluePrint的实例对象object,这里这么做是因为ObjectBluePrint是抽象出来的协议,对于多种类的Object实例类可以方便遵循,后续可以再扩展。在Object实现类的对象中需要注册一些观察者ObserverBluePrint,这样对于需要通知的目标才会清晰。然后当Object出现啦变化,即调用了change方法,那么该方法就会继续调用notify方法,进而逐个让每一个观察者执行update,而show则可以理解为Observer在知道观察目标出现变化之后进行的一些处理动作。(其实Object实现类还可以把自己结构往上提升一级,命名为ObjectCenter,专门用来处理Observer和下级Object的添加和删除,这样的扩展可以自己尝试一下)。以上代码输出结果如下:

Registering Observer... count:1
Registering Observer... count:2
I am Object,and I have already done something
Now I am going to notify Observer
I am Observer 1,I have been notified
Observer 1 can do something for the changed of Object
I am Observer 2,I have been notified
Observer 2 can do something for the changed of Object
Unregistering Observer... count:1
I am Object,and I have already done something
Now I am going to notify Observer
I am Observer 2,I have been notified
Observer 2 can do something for the changed of Object

  总结:观察者模式也叫发布订阅模式,同时也是常常与MVC架构中的MV联系起来(目的是让C减肥),此模式需要记着,直接联想微博关注的人从发消息到你看见的过程大概就能理解,首先是你关注了那个人,那个人发了消息,就会推送到你的页面,你就可以看到,并且可以点赞回复转发什么的,注意的是你不是唯一一个盯着目标的,而且你盯着的目标也不是唯一的,这是一个多对多的关系。多点思考生活中各种事物的联系,是设计模式的一种学习演变过程,因为技术是来源于生活也反馈于生活的。


lZackx © 2022. All rights reserved.

Powered by Hydejack v9.1.6