2011-01-03 5 views
1


노출 된 템플릿 클래스가 있는데 여기에 메서드가 추가되었습니다. 이 클래스는 네임 스페이스 A에 있습니다. 이제이 메서드를 다른 네임 스페이스 (예 : B)에서 호출합니다. 처음에는 컴파일러가이 특정 메서드에 대해 "해결되지 않은 외부 기호"라고 말하는 링커 오류를주었습니다.
그러나이 메서드를 동일한 네임 스페이스 (즉 A) 내에서 호출하면 잘 연결됩니다. 그런 다음 네임 스페이스 B에서도 잘 연결됩니다.
왜 이런 일이 일어날 수 있습니까?
내 클래스의 템플릿 생성 객체와 관련이 있습니까?
아툴
여기 는링커 오류를주는 템플릿 클래스

내가 네임 스페이스 B 내에서이 메서드를 호출하고
namespace sss 
{ 
    namespace AAA 
    { 
     template <<typename T, typename TAlloc = Allocator<T> > 
     class DLL_EXPORT A 
     { 
      public: 
      // Some other functions that are working fine ... 
      bool fooA() const; 
      { 
        return Size()>0; 
      } 
     }; 
    } 
} 


//I get a linker error when I call it in another namespace (say B)... 
//I am accessing this method in public method of some other class in namespace B 

// Including the header for class A ... 
#include A.h 

namespace QQQ 
{ 
    namespace B 
    { 
     class B 
     { 
      private: 
      AAA::A obj; // Object of class A ... 
      public: 
      // SOme methods 
      // Method that calls fooA ... 
      GetResult() 
      { 
       fooA // This causes causes linker error when i call it here, 
        // but, it works when i call it in namespace AAA, 
        // and then it, it works here as well 
      } 
     }; 

, 그것은 내가 네임 스페이스 A를 내에서이 호출 할 때, 그것은 링크, 확인되지 않은 외부 기호를 제공하지만 ... 코드 조각입니다 잘 A에서, 그리고 다시 B에서.
아이디어가 있으십니까?

+0

이를 증명하는 최소한의 코드 예제를 제공 할 수 있습니까? –

+0

코드를 보여줄 수 있습니까? – UmmaGumma

+2

저는 templaet 네임 스페이스가 무엇을 의미하는지 궁금합니다. – UmmaGumma

답변

0

틀린 클래스를 잘못 사용하고 있습니다. 다음은 작동합니다 :이 코드를 상상할 수

namespace QQQ 
{ 
    namespace B 
    { 
     class B 
     { 
      // Note the template parameter (int) 
      AAA::A<int> obj; 

      public: 
      bool GetResult() const 
      { 
       // Note the parentheses and the "obj" 
       return obj.fooA() 
      } 
     }; 
    } 
} 

유일한 문제는 B 네임 스페이스와 B 클래스 사이의 모호한 것이지만, 완전한 호출 (QQQ::B::B)가 작동합니다. 증상 (A 이외의 다른 네임 스페이스에서 호출 링커 오류뿐만 아니라 네임 스페이스 A에서 호출하면 어떤 링커 오류)에 따르면


, 다음 - 당신의 구문이 실제 코드에서 올바른 가정 - 당신의 문제는 템플릿을 올바르게 인스턴스화하지 못한다는 것입니다. 템플릿은 컴파일 타임 구조이므로 실제로는 DLL로 컴파일 할 수 없습니다. 대신 템플릿을 컴파일 할 때 올바르게 인스턴스화해야합니다. 연결 오류가 발생하지 않으면 템플리트가 올바르게 인스턴스화되고 링크 오류가 발생했을 때 오류가 발생했기 때문입니다.

DLL_EXPORT 기호 때문에 나는 Visual C++를 사용하고 있다고 가정합니다. 그렇더라도 GCC 사람들은 Visual Studio에도 적용되는 good write-up을 가지고 있습니다. Boost와 같은 익숙한 대부분의 템플릿 라이브러리는 모든 템플릿을 선언하고 헤더 파일에 정의해야합니다. 또한 템플릿을 명시 적으로 인스턴스화하는 것도 합법적입니다. GCC 사람들이 권장합니다.

0

볼랜드 5 프로페셔널에서도 같은 문제가있었습니다. 외부 참조 메시지와 링커 오류가 있습니다. 해결책은 헤더 끝에 .cpp 파일을 포함시키는 것이 었습니다. 왜냐하면 컴파일러는 템플릿을 인스턴스화 할 수 있도록 전체 정의가 필요하기 때문입니다. 따라서 사용하려는 번역 단위에 정의해야합니다.

희망이 있습니다.