문제

항상 고려하는 다음과 같은 헤더를 포함하는,내 템플릿 클래스가 포함되어 있에서는 적어도 두 개의 .CPP 파일,이 코드를 컴파일하고 올바르게:

template <class T>
class TClass 
{
public:
  void doSomething(std::vector<T> * v);
};

template <class T>
void TClass<T>::doSomething(std::vector<T> * v) {
  // Do something with a vector of a generic T
}

template <>
inline void TClass<int>::doSomething(std::vector<int> * v) {
  // Do something with a vector of int's
}

그러나 참고 인라인에 전문화 방법입니다.이를 방지하기 위해 필요한 링커러(에 VS2008 이 LNK2005)으로 인해 이 방법을 정의되는 한 번 더 다음.저는 이것을 이해하기 때문에 AFAIK 전체 템플릿 전문성과 동일한 간단한 방법으로 정의입니다.

그래서,어떻게 제거하는 inline?코드하지 않아야에서 중복 사용할 때마다습니다.나는 검색이 구글,질문에 여기에 그렇게도 많은 제안된 솔루션을 하지만 아무도는 성공적으로 구축(적어도에 대 2008).

감사합니다!

도움이 되었습니까?

해결책

간단한 기능과 마찬가지로 선언 및 구현을 사용할 수 있습니다. 헤더 선언에 넣으십시오.

template <>
void TClass<int>::doSomething(std::vector<int> * v);

CPP 파일 중 하나에 구현을 넣습니다.

template <>
void TClass<int>::doSomething(std::vector<int> * v) {
 // Do somtehing with a vector of int's
}

인라인을 제거하는 것을 잊지 마십시오 (이 솔루션이 작동하지 않을 것이라고 생각했습니다 :)). VC ++ 2005에서 확인

다른 팁

전문화 정의를 CPP 파일로 이동해야합니다. 템플릿 클래스의 멤버 함수 전문화는 함수가 템플릿으로 선언되지 않더라도 허용됩니다.

키워드 인라인을 제거 할 이유가 없습니다.
어쨌든 코드의 의미를 변경하지 않습니다.

를 제거하려는 경우 인라인 무슨 이유에 대한 솔루션의 maxim1000 완벽하게 유효합니다.

귀하의 의견,지만,그것은 당신을 믿는 인라인 키워드는 기능을 가진 자신의 모든 내용을 가져옵 항상 인라인되지만 AFAIK 는 것은 실제로 매우 의존에서 귀하의 컴파일러 최적화입니다.

에서 인용 C++FAQ

여러 가지 방법이 있을 지정하는 기능입,인라인의 일부 를 포함한 인라인 키워드로,다른 사람하지 않습니다.어떻게 당신 지정 기능으로 인라인 요청입니는 컴파일러가 허용 무시하기:컴파일러도 인라인 확장을 일부 또는 none 의 장소는 함수를 호출로 지정된 인라인 요소입니다.(지 낙심하는 경우에는 길을 막연하다.의 유연성 실제로 거대한 이점:할 수 있는 컴파일러 치료를 큰 기능이 다르게 작은 것부터,플러스 그릴 수 있도록 컴파일러 를 생성하는 코드는 쉽게 디버깅을 선택하면 오른쪽 컴파일러 옵션이 있습니다.)

그래서,는지 알지 못하는 경우에는 해당 기능이 실제로 부풀게 실행하거나지 않는 한 당신이 그것을 제거하려면 템플릿에서 정의 헤더에 대한 다른 이유할 수 있습니다 실제로 떠나는 그가 없이 어떤 피해가

이 조약,그러나 나는 이 경우 여기서 그것은 다른 사람을 도움이 됩니다.나는 인터넷 검색에 대한 템플릿을 전문화를 주도한 여러는 동안@maxim1000 의 대답은 정확하고 궁극적으로 도왔고 그림 밖으로 나의 문제,나는 생각하지 않았다 그것은 풍부하게 분명하다.

나의 상황은 약간 다른 것입니다(하지만 충분히 유사한이 대답 나는 생각한다)보다 OP's.기본적으로,나를 사용하여 타사 라이브러리와 모든 다른 종류의 클래스를 정의하는"상태를 유형".장의 이 유형은 단순히 enums 지만,모든 클래스를 상속에서 일반(초록)부모와 다른 유틸리티 기능과 같은 운영자 과부하고 static toString(enum type) 기능입니다.각각 상태 enum 은 다른 다른 하나에서와 관련이 없습니다.예를 들어,하나는 enum 은 분야 NORMAL, DEGRADED, INOPERABLE, 다른가 AVAILBLE, PENDING, MISSING, 니다,등등.나의 소프트웨어를 담당하는 관리의 다른 형태의 상태에 대한 다른 구성 요소입니다.여하고 싶었다는 것을 활용 toString 기능에 대한 이 enum 클래스,하지만 그 이후 그들은 추상적인 수가 없었 인스턴스화선적으로 적용됩니다.나는 확장된 서류가 사용하고 싶었지만,궁극적으로 나가기로 결정하는 만들기 template 클래스,가 typename 것 무엇이든 콘크리트 상태 enum 나는 걱정에 대해입니다.아마 일부 논쟁이 될 수 있었는 그러한 결정에 대해,그러나 나는 것처럼 느꼈던 많이 보다 더 적은 작업 확장을 각각의 추상 enum 클래스 사용자 지정 중 하나 내 자신의하고 구현하면 추상적인 기능입니다.그리고 물론에서 나의 코드를 호출 할 수 있도록 .toString(enum type) 고 그것을 인쇄하의 문자열 표현하는 enum.이후로 모든 enums 었는 전적으로 관련이 없는,그들 각각 자신 toString 는 기능(후 어떤 연구를 배웠다)가 호출하여 템플릿을 전문화를 만들었습니다.Led 습니다.아래 MCVE 내가 무엇을 해야 했을 만들기 위해 이것이 제대로 작동합니다.실제로 나 솔루션보다 약간 다른@maxim1000 습니다.

이것은(크게 간체)헤더 파일 enums.현실에서,각 enum 클래스에 정의되었다 그것의 자신의 파일입니다.이 파일의 헤더 파일에 제공된 나의 일부분으로 라이브러리 사용:

// file enums.h
#include <string>

class Enum1
{
public:
  enum EnumerationItem
  {
    BEARS1,
    BEARS2,
    BEARS3
  };

  static std::string toString(EnumerationItem e)
  {
    // code for converting e to its string representation,
    // omitted for brevity
  }
};

class Enum2
{
public:
  enum EnumerationItem
  {
    TIGERS1,
    TIGERS2,
    TIGERS3
  };

  static std::string toString(EnumerationItem e)
  {
    // code for converting e to its string representation,
    // omitted for brevity
  }
};

추가 이 라인에 단지 별도의는 다음 파일로 다른 코드 블록

// file TemplateExample.h
#include <string>

template <typename T>
class TemplateExample
{
public:
  TemplateExample(T t);
  virtual ~TemplateExample();

  // this is the function I was most concerned about. Unlike @maxim1000's
  // answer where (s)he declared it outside the class with full template
  // parameters, I was able to keep mine declared in the class just like
  // this
  std::string toString();

private:
  T type_;
};

template <typename T>
TemplateExample<T>::TemplateExample(T t)
  : type_(t)
{

}

template <typename T>
TemplateExample<T>::~TemplateExample()
{

}

다음 파일

// file TemplateExample.cpp
#include <string>

#include "enums.h"
#include "TemplateExample.h"

// for each enum type, I specify a different toString method, and the
// correct one gets called when I call it on that type.
template <>
std::string TemplateExample<Enum1::EnumerationItem>::toString()
{
  return Enum1::toString(type_);
}

template <>
std::string TemplateExample<Enum2::EnumerationItem>::toString()
{
  return Enum2::toString(type_);
}

다음 파일

// and finally, main.cpp
#include <iostream>
#include "TemplateExample.h"
#include "enums.h"

int main()
{
  TemplateExample<Enum1::EnumerationItem> t1(Enum1::EnumerationItem::BEARS1);
  TemplateExample<Enum2::EnumerationItem> t2(Enum2::EnumerationItem::TIGERS3);

  std::cout << t1.toString() << std::endl;
  std::cout << t2.toString() << std::endl;

  return 0;
}

이 출력:

BEARS1
TIGERS3

이 없는 경우에 이상적인 솔루션을 내 문제를 해결,하지만 그것이 나를 위해 일했습니다.지금 아무리 많은 열거형 나는 끝까지 사용하여,내가 할 일은 몇 줄을 추가한 toString 방법니다.cpp 파일을 사용할 수 있는 라이브러리 이미 정의 toString 메소드를 구현하지 않고 그 자신을 확장하지 않고 각 enum 클래스 I 이 사용하고 싶습니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top