有時候我們會被問到JS中的觀察者模式,其實這個這個模式大家都了解過的,可以說,它是動態語言中非常有用的設計模式。今天武林技術頻道小編馬上為大家介紹js中的觀察者模式的實現方法。
觀察者模式
關于觀察者模式,《松本行弘的程序世界》講的非常清楚:觀察者模式是當某個對象狀態發生變化時,依存于該狀態的全部對象自動得到通知,被觀察者和觀察者們是一對多的關系。書中還舉了一個非常易懂的例子:獲取系統當前時間并輸出到命令行中。如果要硬編碼也很簡單,定義一個方法,先獲取時間,然后再處理展示。這樣獲取時間的功能基本就不能復用了,因為帶了個處理展示的拖油瓶。
如果用觀察者模式則可以這樣:定義兩個類,一個用于計時,獲取當前時間;另一個用于展示時間。展示時間的類就是觀察者,這樣做的好處是降低相互的依賴性。第一個類改變后不需要處理任何事物,只需要發出通知告訴它的觀察者們,具體事物由它們處理。比如有一天我們想換種形式展示時間,或者用多種方式展示時間,完全不需要牽扯到第一個類。
PS:《松本行弘的程序世界》真是一本好書。起初是想把這本書當做ruby教程來讀的,后來發現根本不是,書中用非常易懂的語言深入淺出的講明白了很多深奧的哲學思想。雖然這本書對我這種剛入門的菜鳥來說幾乎沒有什么實用價值,但是讀完之后有種豁然開朗的感覺,是一次非常好的閱讀體驗。
ruby實現
用ruby實現觀察者模式簡直簡單清晰的令人發指,上代碼:
?
復制代碼 代碼如下:
require "observer"
#被觀察者
class Subject
??? include Observable
??? def notify
??????? #do sth
??????? changed #更新標志為真
??????? notify_observers(*args) #如果更新標志為真,調用觀察者帶參數args的方法
??? end
end
#觀察者
class Obs
??? #回調函數,好像只能這么叫
??? def update
??????? #do sth
??? end
end
#實例
sub = Subject.new
sub.add_observer(Obs.new)
sub.notify
?
沒錯,就是這么簡單。。。
主要是依靠Observer模塊,除了上面用到的,此模塊還有如下接口:
1.delete_observer(obj) 刪除特定的觀察者
2.delete_observers 刪除全部觀察者
3.count_observers 獲取觀察者數目
4.changed? 檢查更新標志
php實現
php實現起來也不麻煩:
復制代碼 代碼如下:
//被觀察者
class Subject
{
??? private $_observers;
??? public function __construct() {
??????? $this->_observers = array();
??? }
??? public function add_observer($obs) {
??????? $this->_observers[] = $obs;
??? }
??? public funtion delete_observer($bos) {
??????? $index = array_search($bos, $this->_observers);
??????? unset($this->_observers[$index]);
??? }
??? public function notify_observers() {
??????? foreach($this->_observers as $v) {
??????????? $v->update();
??????? }
??? }
}
//觀察者
class Observer
{
??? public function __construct() {
??????? do sth;
??? }
??? public function update() {
??????? do sth;
??? }
}
//實例
$sub = new Subject();
$obs = new Observer();
$sub->add_observer($obs);
$sub->notify_observers();
?
js實現
js實現起來也不麻煩,就是得寫些工具函數方便用,比如刪除數組指定的元素。下面只用最簡單的實現方法。
復制代碼 代碼如下:
//被觀察者
function Subject() {
??? var _this = this;
??? this.observers = [];
??? this.addObserver = function(obj) {
??????? _this.observers.push(obj);
??? }
??? this.deleteObserver = function(obj) {
??????? var length = _this.observers.length;
??????? for(var i = 0; i < length; i++) {
??????????? if(_this.observers[i] === obj) {
??????????????? _this.observers.splice(i, 1);
??????????? }
??????? }
??? }
??? this.notifyObservers = function() {
??????? var length = _this.observers.length;
??????? console.log(length)
??????? for(var i = 0; i < length; i++) {
??????????? _this.observers[i].update();
??????? }
??? }
}
//觀察者
function Observer() {
??? this.update = function() {
??????? alert(1)
??? }
}
var sub = new Subject();
var obs = new Observer();
sub.addObserver(obs);
sub.notifyObservers();
var sub = new Subject();
?
結論:ruby可以讓我們專注于程序設計本身,而不是程序的語法和特性。js靈活多變,是一門完備的編程語言除了生孩子什么都能實現,就是玩起來要下點功夫。php嘛,中規中矩,沒啥好說的。
通過上文介紹的js中的觀察者模式的實現方法,相信大家了解了不少啦。如不明白的話,給武林技術頻道小編留言,我們會讓你徹底明白!