實作 QueryInterface 的規則
在 COM 對象上實 作 IUnknown::QueryInterface 方法有三個主要規則:
- 對象必須具有身分識別。
- 對象實例上的介面集合必須是靜態的。
- 必須能夠從任何其他介面成功查詢物件上的任何介面。
對象必須具有身分識別
對於任何指定的物件實例,對具有 IID_IUnknown的 QueryInterface 呼叫一律必須傳回相同的實體指標值。 這可讓您在任何兩個介面上呼叫 QueryInterface ,並比較結果,以判斷它們是否指向物件的相同實例。
對象實例上的介面集必須是靜態的
透過 QueryInterface 在物件上存取的介面集合必須是靜態的,而不是動態的。 具體來說,如果 QueryInterface 傳回指定 IID 的S_OK一次,它絕對不能在相同對象的後續呼叫上傳回E_NOINTERFACE;如果 QueryInterface 傳回指定 IID 的E_NOINTERFACE,則相同物件上相同 IID 的後續呼叫絕對不能傳回S_OK。
必須能夠成功查詢來自任何其他介面之物件上的任何介面
也就是說,假設有下列程序代碼:
IA * pA = (some function returning an IA *);
IB * pB = NULL;
HRESULT hr;
hr = pA->QueryInterface(IID_IB, &pB);
適用下列規則:
如果您有物件上介面的指標,則相同介面的 QueryInterface 呼叫必須成功:
pA->QueryInterface(IID_IA, ...)
如果第二個介面指標的 QueryInterface 呼叫成功,則從第一個介面的該指標呼叫 QueryInterface 也必須成功。 如果成功取得 pB,下列項目也必須成功:
pB->QueryInterface(IID_IA, ...)
任何介面都必須能夠查詢物件上的任何其他介面。 如果成功取得 pB,且您已成功使用該指標查詢第三個介面 (IC),您也必須能夠使用第一個指標 pA 成功查詢 IC。 在此情況下,下列順序必須成功:
IC * pC = NULL; hr = pB->QueryInterface(IID_IC, &pC); pA->QueryInterface(IID_IC, ...)
介面實作必須維護指定物件上所有介面之未處理指標參考的計數器。 您應該針對計數器使用 不帶正負號的整數 。
如果客戶端必須知道已釋放資源,它必須在物件上具有較高層級語意的某個介面中使用 方法,才能呼叫 IUnknown::Release。
相關主題