2014-05-01 4 views
2

두 개의 COM 인터페이스 포인터 (예 : ID3D11Texture2D)가 있고 기본 클래스 인스턴스가 동일한 지 확인하려면 두 포인터를 직접 비교하여 평등하게 비교할 수 있습니까? 나는 비교가 끝나기 전에 뭔가 다른 것에 던져 넣은 코드를 보았습니다. 그래서 확인하고 싶었습니다.COM 포인터가 같은지 확인하십시오.

BOOL IsEqual (ID3D11Texture2D *pTexture1, ID3D11Texture2D *pTexture2) 
{ 
    if (pTexture1 == pTexture2) 
    { 
     return true; 
    } 
    else 
    { 
     return false; 
    } 
} 

감사합니다.

답변

7

올바른 COM 방법은 IUnknown을 사용하여 인터페이스를 쿼리하는 것입니다. MSDN의 발언 here에서 인용 : 어떤 하나의 객체에 대한

, 객체의 인터페이스의 의 IUnknown 인터페이스에 대한 특정 쿼리는 항상 같은 포인터 값을 반환해야합니다. 이렇게하면 클라이언트가 IID_IUnknown과 QueryInterface를 호출하고 결과를 비교하여 을 호출하여 두 개의 포인터가 동일한 구성 요소를 가리키는 지 여부를 확인할 수 있습니다. 특히 에 대한 쿼리가 IUnknown 이외의 인터페이스 (같은 인터페이스 인 을 통해 동일한 인터페이스 일 수도 있음)가 동일한 포인터 값을 반환해야하는 경우가 아닙니다.

그래서 올바른 코드는

BOOL IsEqual (ID3D11Texture2D *pTexture1, ID3D11Texture2D *pTexture2) 
{ 
    IUnknown *u1, *u2; 

    pTexture1->QueryInterface(IID_IUnknown, &u1); 
    pTexture2->QueryInterface(IID_IUnknown, &u2); 

    BOOL areSame = u1 == u2; 
    u1->Release(); 
    u2->Release(); 

    return areSame; 
} 

업데이트

  1. 추가 그래서 해제 참조 횟수를 감소 할 수있는 호출입니다. 좋은 코멘트 주셔서 감사합니다.
  2. 이 작업에는 ComPtr을 사용할 수도 있습니다. MSDN에서 확인하십시오.
+2

해당 포인터에서'Release()'를 호출해야한다는 것을 잊지 마십시오. –

+0

포인터 비교가 필요하기 전에 왜 IUKnown에 대한 QI를 볼 수 있습니다. 그러나 나는 실용 주의적 관점에서 이것을 이해하려고 애를 쓰고있다. 인터페이스 포인터는 기본 클래스가 구현하는 인터페이스 메소드에 대한 vtbl 포인터입니다. 사실, 내가 본 QI의 대부분의 구현은 "this"포인터의 단순한 static_cast이며, 단순히 클래스 구현의 메모리 레이아웃을 탐색하여 vtbl 포인터를 얻습니다. 따라서 동일한 포인터를 통해 같은 인터페이스를 사용하는 QI 인 경우 어떤 상황에서 동일한 포인터를 반환하지 않을지 궁금하지 않습니다. – lancery

+0

@lancery - COM ID는 IUnknown에만 있습니다. 일부 구현은 같은 포인터를 배경으로 반환하지만 다른 IID에 대해서는 아무 것도 가정 할 수 없습니다. 또한 다음을 확인하십시오 : http://msdn.microsoft.com/en-us/library/windows/desktop/ms686590(v=vs.85).aspx –

관련 문제