2012-08-22 3 views
3

간단히하기 위해 두 개의 DLL_TUTORIAL.dll을 헤더 MathFuncsDll.h에 루트 폴더 C : \에 넣었습니다. \ DLL_TUTORIAL :지연로드 DLL

그런 다음

구성 속성 -> 링커 -> 입력 -> 지연의 DLL의

에 C 부하 설정 빈 프로젝트를 생성 .dll; % (DelayLoadDLLs)

구성 속성 -> VC++ 디렉토리 -이> 포함 디렉토리

C에 : \; $ (IncludePath)

컴파일러 명령 :

/Zi/nologo/W3/WX-/O2/Oi-/GL/D "_MBCS"/ Gm-/EHsc/MT/GS /Gy/fp : 정밀도/Zc : wchar_t/Zc : forScope /Fp"Release\clean_rough_draft.pch "/ 빠"릴리스 \ "/ FO"릴리스 \ " /Fd"Release\vc100.pdb"/ 하나님/analyze-/errorReport : 큐

이 프로젝트 main이있는 파일 만 포함합니다.

MAIN.CPP

#include <Windows.h> 
#include <iostream> 
#include "MathFuncsDll.h" 

using namespace MathFuncs; 
using namespace std; 

int main() 
{ 
    std::cout<< MyMathFuncs<int>::Add(5,10)<<endl; 

    system("Pause"); 
    return 0; 
} 

의 DLL은 다른 솔루션에서 성공적으로 운영되고 있습니다. 이러한 기능

MathFuncsDll.h

namespace MathFuncs 
{ 
    template <typename Type> 
    class MyMathFuncs 
    { 
    public: 
     static __declspec(dllexport) Type Add(Type a, Type b); 

     static __declspec(dllexport) Type Subtract(Type a, Type b); 

     static __declspec(dllexport) Type Multiply(Type a, Type b); 

     static __declspec(dllexport) Type Divide(Type a, Type b); 

    }; 


} 

설명 :

#include "MathFuncsDll.h" 

#include <stdexcept> 

using namespace std; 

namespace MathFuncs 
{ 
    template <typename Type> 
    Type MyMathFuncs<Type>::Add(Type a,Type b) 
    { return a+b; } 

    template <typename Type> 
    Type MyMathFuncs<Type>::Subtract(Type a,Type b) 
    { return a-b; } 

    template <typename Type> 
    Type MyMathFuncs<Type>::Multiply(Type a,Type b) 
    { return a*b; } 

    template <typename Type> 
    Type MyMathFuncs<Type>::Divide(Type a,Type b) 
    { 
     if(b == 0) throw new invalid_argument("Denominator cannot be zero!"); 
     return a/b; 
    } 
} 

이 프로그램 실행이 실패

1> main.obj : 오류 LNK2001 :되지 않은 외부 기호 " public : static int __cdecl MathFuncs :: MyMathFuncs :: Add (int, int) "? @? $ MyMathFuncs @ H @ MathFuncs @@ SAHHH @ Z),210 1> C : \ 사용자 메크 \ 문서가 프로젝트 \ 비주얼 스튜디오 2010 \ \ \ clean_rough_draft \ clean_rough_draft.exe 릴리스 \ : 치명적인 오류 LNK1120 : 1 개 확인되지 않은 외부 내 실수를 지적 할 수

?

+2

템플릿 방법 내보내기가 지원되지 않습니다. .h 파일에 넣어야 할 것이다. 빈 DLL을 남겨 둡니다. –

+0

정교하게 말하면, 템플릿 메소드는 "실제"메소드가 아닙니다. 템플릿 메소드는 컴파일 타임에 메소드를 생성하는 데 사용되는 금형입니다. 따라서 템플릿 메소드는 객체 코드로 컴파일되지 않습니다. – nakiya

답변

3

이 문제는 지연된 DLL로드와 관련이 있거나없는 것과 관련이 있습니다.여기에 두 가지 문제점이 있습니다.

  1. 템플릿 기능을 내보내고 있습니다. 템플릿 내보내기는 Visual C++ 컴파일러에서 지원되지 않지만 이미 표준에서 제외 되었기 때문에 이렇게 작동하지 않습니다. 이 작업을 수행하려면 두 가지 가능한 솔루션이 있습니다.

    • .h 파일의 메서드 구현을 옮기십시오. 따라서 모든 코드가 헤더 파일에 있으므로 더 이상 DLL이 필요하지 않습니다.
    • 클라이언트 응용 프로그램에서 사용할 유형으로 템플릿을 인스턴스화하십시오. 이것은 헤더 파일에 extern template 선언을하는 등 정확한 유형의 인스턴스화 코드를 cpp 파일에 넣는 것입니다. 자세한 내용은 Google에서 찾아 볼 수 있습니다. 'extern template DLL'또는 유사 항목 만 검색하면됩니다.
  2. DLL을 만들 때만 메서드를 내보내지만 절대로 가져 오지 마십시오 (코드에서 볼 수있는 것이 이상). 각 메서드 앞에 __declspec(dllexport)을 사용하면 해당 메서드를 DLL에 넣도록 컴파일러에 지시합니다. 클라이언트 응용 프로그램에서이 메서드를 사용하려면 DLL에서 해당 메서드를 가져와야합니다. 이는 각 방법 앞에 __declspec(dllimport)을 배치하여 수행됩니다. 메서드에 두 접두사를 둘 수 없기 때문에 메서드 접두사의 경우와 다른 두 개의 거의 동일한 헤더 파일을 만들어야하거나 DLL 작성 코드 또는 클라이언트 응용 프로그램인지 여부에 따라 매크로 대체를 사용해야합니다. 다시 한번, 당신은 구글에서 그것을 어떻게 볼 수 있습니다.

나는 희망한다.