2010-06-03 11 views
1

이전 게시물에 대한 좋은 통찰력이 있었지만 이러한 컴파일 오류로 인해 보조자를 사용할 수 있다는 것을 알 수 없습니다. 템플릿, 친구, 오버로드는 모든 새로운, 그래서 3 1친구, 템플릿, 오버로드 << 링커 오류

#ifndef POINT_H 
#define POINT_H 

#include <iostream> 

template <class T> 
class Point 
{ 
public: 
Point(); 
Point(T xCoordinate, T yCoordinate); 
template <class G> 
friend std::ostream &operator<<(std::ostream &out, const Point<G> &aPoint); 

private: 
T xCoordinate; 
T yCoordinate; 
}; 

#endif 

Point.cpp

에게 나에게
#include "Point.h" 

template <class T> 
Point<T>::Point() : xCoordinate(0), yCoordinate(0) 
{} 

template <class T> 
Point<T>::Point(T xCoordinate, T yCoordinate) : xCoordinate(xCoordinate), yCoordinate(yCoordinate) 
{} 


template <class G> 
std::ostream &operator<<(std::ostream &out, const Point<G> &aPoint) 
{ 
std::cout << "(" << aPoint.xCoordinate << ", " << aPoint.yCoordinate << ")"; 
return out; 
} 

주를 몇 가지 문제 ...

1>main.obj : error LNK2019: unresolved external symbol "public: __thiscall Point<double>::Point<double>(double,double)" ([email protected]@@[email protected]@Z) referenced in function _main 
1>main.obj : error LNK2019: unresolved external symbol "public: __thiscall Point<int>::Point<int>(int,int)" ([email protected]@@[email protected]@Z) referenced in function _main 
1>C3_HW8.exe : fatal error LNK1120: 3 unresolved externals 

Point.h을주고있다 .cpp

#include <iostream> 
#include "Point.h" 

int main() 

    { 
    Point<int> i(5, 4); 
    Point<double> *j = new Point<double> (5.2, 3.3); 
    std::cout << i << j; 
    } 
+1

BTW는 컴파일러 오류가 아닌 링커 오류입니다. 문제는 컴파일러가 템플릿 함수 정의를 컴파일하지 않았기 때문에 컴파일 할 T 코드를 모르기 때문입니다. – Troubadour

답변

5

대부분의 컴파일러에서 요 헤더에 템플릿을 넣어야하므로 컴파일러가 템플릿을 사용할 수 있습니다. 정말로 피하기를 원한다면 필요한 유형에 대해 템플릿을 명시 적으로 인스턴스화 할 수 있지만 헤더에 두는 것이 훨씬 더 일반적입니다.

0

Point 클래스는 main 함수와 동일한 프로젝트 내에서 정의되고 컴파일됩니까? 컴파일시 템플릿이 해석되므로 두 번째 프로젝트에서 템플릿을 정의 할 수 없습니다 (예 : 정적 라이브러리 및 링크). 별도의 프로젝트에서 원한다면 헤더 내에 전체 구현을 제공하고 템플릿의 소스 파일을 생략해야합니다. 해당 헤더를 포함하면 주 함수가있는 파일을 컴파일 할 때 템플릿이 실제 인스턴스화를 위해 컴파일됩니다 (Point and Point).

클래스를 사용하려면 링크가 필요하며 템플릿 헤더로 구성된 프로젝트는 링크 가능 라이브러리를 생성하지 않습니다.