您好,登錄后才能下訂單哦!
觀察者模式
二話不說,上來就是定義
定義對象間的一種一對多的依賴關系,當一個對象的狀態發送改變時,所有依賴于它的對象都能得到通知并被自動更新
這個好像還好理解那么一點點,不過還是先來講個情景,
天氣預報的短信服務,一旦付費訂閱,每次天氣更新都會向你及時發送
其實就是我們無需每時每刻關注我們感興趣的東西,我們只需要訂閱它即可,一旦我們訂閱的事務有變化了,被訂閱的事務就會即時的通知我們
我們來看一下觀察者模式的組成:
觀察者,我們稱它為Observer,有時候我們也稱它為訂閱者,即Subscriber
被觀察者,我們稱它為Observable,即可以被觀察的東西,有時候還會稱之為主題,即Subject
至于觀察者模式的具體實現,java里為我們提供了Observable類和Observer接口供我們快速實現該模式,但是這里為了加深印象,不用這個兩個類,以下是觀察者模式的代碼實現:
1、首先我們定義一個的接口,里面是觀察者需要做的三件事:
public interface ObjectAble {
public void add(ObjectSerType type, ObjectServer obj);//添加訂閱
public void remove(ObjectSerType type, ObjectServer obj);//取消訂閱
void notifyDataChange(ObjectSerType type, Object... objs);//發送訂閱內容
}
2、當主題發生變化的時候,需要通知觀察者來做出響應,還需要一個onRecever方法,具體實現如下
public interface ObjectServer {
void onRecever(Object...obj);
}
3、定義觀察者類型的枚舉類,這是表示觀察者的類型,當觸發ObjectAble 接口中的notifyDataChangee(ObjectSerType type, Object... objs)方法時,即主題發生變化,所有類型為type的已訂閱的觀察者會被觸發。
package com.example.testobjectserver;
public enum ObjectSerType{
a,b,c,d
}
4、實現ObjectAble接口,為每個方法添加邏輯
package com.example.testobjectserver;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import android.util.Log;
public class ObjectAbleImpelet implements ObjectAble {
public static ArrayList<HashMap<ObjectSerType, ObjectServer>> ObjectServerList = new ArrayList<HashMap<ObjectSerType, ObjectServer>>();
static ObjectAbleImpelet instance = null;
public static ObjectAbleImpelet getInstance() {
synchronized (ObjectAbleImpelet.class) {
if (instance == null)
instance = new ObjectAbleImpelet();
}
return instance;
};
@Override
public void add(ObjectSerType type, ObjectServer obj) {
if (type == null && obj == null)
throw new NullPointerException("ObjectSerType or ObjectServer can not null");
synchronized (ObjectServerList) {
HashMap<ObjectSerType, ObjectServer> map = new HashMap<ObjectSerType, ObjectServer>();
map.put(type, obj);
ObjectServerList.add(map);
Log.e("", "ObjectServerList>>>" + ObjectServerList);
}
}
@Override
public void remove(ObjectSerType type, ObjectServer obj) {
for (HashMap<ObjectSerType, ObjectServer> map : ObjectServerList) {
Log.e("", "type>>>" + type);
if(map.get(type).equals(obj)){
ObjectServerList.remove(map);
Log.e("", "obj>>>" + obj);
break;
}
}
}
@Override
public void notifyDataChange(ObjectSerType type, Object... objs) {
for (int i = 0; i < ObjectServerList.size(); i++) {
HashMap<ObjectSerType, ObjectServer> map = ObjectServerList.get(i);
if (map.containsKey(type)) {
map.get(type).onRecever(objs);
}
}
}
}
5、測試:
package com.example.testobjectserver;
import android.app.Activity;
import android.os.Bundle;
import android.util.Log;
import android.view.Menu;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.TextView;
public class MainActivity extends Activity implements ObjectServer {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ObjectAbleImpelet.getInstance().add(ObjectSerType.a, this);//添加訂閱,類型為ObjectSerType.a, 類型由開發者定義
findViewById(R.id.button1).setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
ObjectAbleImpelet.getInstance().notifyDataChange(
ObjectSerType.a, "你好");//主題發生變化,觸 //發所有類型為ObjectSerType.a的觀察者調用onRecever方法
}
});
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
//主題變化后,觀察者的回調
@Override
public void onRecever(Object... obj) {
Log.e("", "我是觀察者!!!" + (String) obj[0]);
((TextView) findViewById(R.id.textView1)).setText("" + (String) obj[0]);
}
@Override
protected void onDestroy() {
//無論如何,當退出activity,該activity中的觀察者需要被回收,不然會導致觀察者容器中的觀察者
//對象越來越多
ObjectAbleImpelet.getInstance().remove(ObjectSerType.a, this);
super.onDestroy();
}
}
6、如下圖所示:進入activity注冊類型為a的觀察者,當點擊按鈕,觸發onRecive回調,更新ui;退出activity時注銷觀察者。該觀察者完成使命
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。