Singleton,確保類別永遠只有一份實體
Singleton pattern, 簡言之,是一個確保類別永遠只有一份實體的範式(Pattern).
在什麼情況下,我們會用到這個 Pattern 呢??
比如,一台電腦裡在同一時間只能有一個視窗管理員在運行.
一般性的做法,是讓類別自行管理這個唯一個物件實體,讓他確保絕對無法生出第二個物件個體.
那麼在 VFP 裡面要如何實現呢??
讓我們來試試看,首先先定義出 CSingleton 這個Class
*
* Class Singleton
*
DEFINE CLASS CSingleton as Custom
HIDDEN m_singleton
m_singleton=.NULL.
PROCEDURE getInstance
IF m_singleton==.NULL.
m_singleton=CREATEOBJECT(“CSingleton”)
ENDIF
RETURN m_singleton
ENDPROC
PROCEDURE getClassName
return “I am Singleton Class”
ENDPROC
ENDDEFINE
我們將 m_singleton 隱藏起來,讓外界無法直接存取,並且提供 getInstance method,讓外界可以透過此 method 取得 m_singleton 這個 instance.
所以當我們需要這個類別的實體時,就可以這麼寫:
lo_object=CSingleton::getInstance()
嘿,等等,別的語言是可以這麼寫,VFP 允許我們這樣用嗎??
此外,我們也沒有辦法隱喻地將 m_instance 放到 heap,像別的語言可以用 static 表明 m_instance 要放到 heap 中,確保只會有一份實體.
VFP 必須要先為 CSingleton 類別產生實體,才能呼叫 getInstance()
也就是要先這樣子
local lo_class, lo_object
lo_class=createobject(“CSingleton”)
lo_object=lo_class.getInstance()
才能讓 lo_object 取得實體.
那這不就違反我們的本意了嗎??
當使用者呼叫了多次 createobject(“CSingleton”), 等於是創建了好幾次 m_singleton,我們就無法讓 m_singleton 是系統中唯一的一個實體了.
那麼還有別的方法嗎??
嗯,用全域變數如何??
我們可以用全域變數搭配一個Function來使用.
所以就可以這麼寫
public m_instance
….
* 主程式
m_instance=.null.
…
* Function
function getInstance
if m_instance==.null.
m_instance=createobject(“CSingleton”)
endif
return m_instance
endfunc
…
* 要使用的時候
lo_object=getInstance()
? lo_object.getClassName()
…
這樣子總算是解決問題了,只要維持一個良好的撰寫習慣
就可以保證CSingleton的實體是唯一.
可是萬一後繼者不明白,直接去存取了全域變數 m_instance 的話,該怎麼辦呢??
嗯~~再換個方向來想
VFP 不是有個函數叫做 getobject() 嗎??
如果我們將類別轉為 OLEPUBLIC 之後,再使用 getobject() 去取得 instance,就可以取得唯一的實體來使用了.
這也不失為一個不錯的解法.
綜觀上面推論,或許還有其他的方法,是我沒有想到的.(我有想過用 fopen() 或 flock()…等等的)
但是就目前看來,在 VFP 裡面對 Singleton 並沒有一個完美的解法.
只有期待 VFP 未來能加入新的語言特性,讓我們能更靈活的運用了.
附錄: C++ 的解法
class CSingleton {
private:
static CSingleton* m_instance;
protected: //保護起來,不讓 constructor 直接被叫用.
Singleton();
Singleton(const Singleton&);
Singleton& operator= (const Singleton&);
public:
CSingleton* getInstance(void) {
if( m_instance==NULL )
m_instance=new CSingleton();
return m_instance;
}
char* getClassName(void) {
return “Hello! Singleton Pattern!!\n”;
}
}
CSingleton* CSingleton::m_instance=NULL; //因為宣告為 static,所以可以這樣給值.
int main( int argc, char* argv[] ) {
CSingleton* obj=CSingleton::getInstance;
printf( “%s”, obj->getClassName());
}
NERV
閒聊的時候,聊到NERV與福音戰士,於是查了一下,在這裡居然有解釋.
NERV:在德文中,這個詞是指”神志”.在劇中,NERV是”人類補完計劃”委員會的一個直屬特務機關,負責開發和使用EVA機與使徒進行戰鬥,他們擁有很高的科技成果和極高的軍事許可權,從三賢人超級電腦和葛城在必要的時候可以調動整個日本的電力就可見一斑.
SEELE:這個詞在德文中是指”心靈”.不要忘記,日本人一直都喜歡在作品中提到德國,而明日香更是有德國血統呢.庵野秀明有意的運用NERV和SEELE做劇中兩個組織的名字,其用心在向觀衆表明一些什麽呢?