如何確保只有通過另一個特定對象才能實例化對象?如何確保特定對象僅由另一個對象實例化?
例如,假設我有一個Registry對象來存儲Mappers。當客戶端代碼在註冊表中調用get()
方法時,它懶惰地加載並返回請求的映射器。這很好,除了沒有什麼可以阻止客戶端代碼使用new
運算符創建映射器的重複實例。
我能想到的唯一選擇是我的Mappers需要一個Registry對象作爲參數。還有其他選擇嗎?
你是做什麼的?我是否應該避免這種重複?
如何確保只有通過另一個特定對象才能實例化對象?如何確保特定對象僅由另一個對象實例化?
例如,假設我有一個Registry對象來存儲Mappers。當客戶端代碼在註冊表中調用get()
方法時,它懶惰地加載並返回請求的映射器。這很好,除了沒有什麼可以阻止客戶端代碼使用new
運算符創建映射器的重複實例。
我能想到的唯一選擇是我的Mappers需要一個Registry對象作爲參數。還有其他選擇嗎?
你是做什麼的?我是否應該避免這種重複?
也許你不應該試圖阻止人們自己創建實例嗎?如果你不相信你自己或你的同事不要在不應該實例化它們的地方實例化對象,那你就有問題。
如果映射器不需要註冊表來運行,則不應該通過構造函數來對其進行反對。將它傳遞給一些靜態方法似乎很奇怪,並且使得你的代碼因爲使用靜態而變得更加靈活。你將如何單元測試映射器,而無需編寫一些黑客程序,通過註冊表正確地實例化它們,這些測試中不需要這些註冊表?好的帖子在這裏:http://kore-nordmann.de/blog/0103_static_considered_harmful.html
您無法保護new
運營商。你可以做的是,你的類中有一個get()
方法來創建你的類/對象單例(或者像你一樣使用註冊表)。
class clTest {
private static $oInstance;
public static function get() {
if(!self::$oInstance) {
self::$oInstance = new clText;
}
return self::$oInstance;
}
}
,如果你想防止外界實例你只需要聲明__construct私營然後用調用一個靜態方法來獲取映射類的一個實例。然後,您可以傳入註冊表類的實例,並且只有在參數是註冊表類的實例時才返回新實例。
class Mapper{
private __construct(){}
public static function getInstance($registry){
if($registry instanceof Registry){
return new Mapper();
}
}
}
$registry = new Registry();
$mapper = Mapper::getInstance($registry);
也許我沒有得到你的問題,但爲什麼你不宣佈Mapper靜態? –