2012-01-08 2 views
3

저는이 문제에 대한 연구를 해왔지만 아직 해결 방법을 찾지 못했습니다. 기본적으로 템플릿 클래스 내에서 정적 const 형식 변수를 초기화해야합니다.정적 클래스 형식의 템플릿 클래스

class MyType 
{ 
public: 
    MyType (int a, int b) { } 
}; 

template <class T> 
class MyClass 
{ 
public: 
    static const MyType Type; 
}; 

cpp 내부의 초기화 유형은 링커 오류를 생성합니다. 헤더 안의 Type을 초기화하면 여러 번 초기화됩니다. 클래스 내부의 초기화 타입은 정수 타입이 아니기 때문에 초기화 할 수 없습니다. 클래스 전문화를 제한하지 않고 어떻게이 문제를 해결할 수 있습니까? 어떤 도움을 주셔서 감사합니다.

+0

"머리글 내부에서 초기화 형식을 사용하면 여러 번 초기화 될 수 있습니다." 어떻게 그 일을 정확하게 할 수 있습니까? 생성자가 두 번 이상 호출되는지 여부를 단순히 확인하는 경우 템플릿 클래스 인스턴스화 당 하나의 멤버가 있으므로 두 번 이상 호출해야합니다. – hvd

답변

3

"cpp에서 Type을 초기화하면 링커 오류가 발생합니다."라는 것이 무슨 뜻인지 확실하지 않습니다. 그러나 실제로는 으로 정의되었다고 가정하면, 적절한 위치에있는 모든 유형의 정적 멤버를 확실히 정의 할 수 있기 때문에 잘못된 결과가 발생했을 것입니다! 클래스 템플릿에있는 것은 객체의 선언이며 이것을 참조하면 어딘가에 정의해야합니다. MyType이 필수 유형 인 경우에만 [템플릿] 클래스에서 초기화하면 절대 정의하지 않고 빠져 나간 것처럼 주소가 필요하지 않습니다 (예 : 상수 참조에 바인딩하거나 주소를 가져옴). 이 경우 항상 상수 표현으로 취급되기 때문입니다.

내 생각 엔 당신이 어떤 CPP 파일에서이 같은 개체 뭔가를 정의하려고한다는 것입니다 : 당신은 또한 같은 번역 단위에서 명시 적 또는 암시 적으로이 정의를 인스턴스화하지 않는 한이 작동하지 않습니다

template <typename T> MyType const MyClass<T>::Type = some-initialization-here; 

. 당신은 실제로 당신이 일반적으로 측면 단계 수있는 경우 문제를 상수 표현으로 유형을 필요로하지 않는 한 그에게 enum을함으로써 필요한 경우

template <> MyType const MyClass<T>::Type = some-initialization-here; 

:이 같은 특정 유형의 뭔가 구성원을 정의 할 수 있습니다

template <typename T> 
MyType const& MyClass<T>::Type() { 
    static MyType rc = some-initialization-here; 
    return rc; 
} 

가 BTW, 나는 ': 대신 헤더에 정의 할 수 있습니다 정적 멤버 함수를 사용할 수 있습니다 (이것은이 사람이 정의를 필요로하지 않고 const 참조에 바인드 할 수 있기 때문에 내가하는 경향 것입니다) 확실히이 질문에 대한 답변은 전에 확실히 comp.lang.c++.moderated입니다.

+0

이 함수는 여전히'MyClass'가 다중'MyType' 객체를 포함하도록합니다. 그 외에 +1. 함수 - 로컬 통계는 정적 초기화 순서 실패로 인해 클래스 로컬 또는 전역 통계보다 우수합니다. – Xeo

+0

@ Xeo : 물론, 인스턴스화마다 하나의 개체가 있습니다. 이것을 원하지 않는다면 정적 멤버를 일반적인 [템플릿 화되지 않은] 기본 클래스로 인수 분해해야합니다. –

1

머리글 내부의 초기화 형식은 여러 번 초기화됩니다.

물론, 물론입니다. MyClass이 인스턴스화되는 모든 유형마다 한 번. 또한 모든 유형에 대해 다른 객체이기 때문에 템플릿이 작동하는 방식에 고유합니다. 당신은 단지 원하는 경우 정의 한 번 초기화, 비 템플릿 기반에 넣어 :

namespace detail{ 
class MyClassBase{ 
protected: 
    ~MyClassBase(){} // only usable as a base class, non-polymorphic 
    static const MyType Type; // only available to derived types 
}; 
} // detail:: 

template<class T> 
class MyClass 
    : private detail::MyClassBase // private, non-polymorphic 
{ 
public: 
    using MyClassBase::Type; // if you want to expose 'Type' to the public audience 
}; 

지금 당신은 단지 통화 당에
const MyType detail::MyClassBase::Type = /*initialize here*/; 

을 넣을 수 있고 함께 할 수. 일반적 @Dietmar 볼 수 있듯이, 함수 내부 static 객체를 캡슐화 좋을 것이라고


참고. 그 함수 - 지역 통계는 다른 종류의 정적 객체보다 우수합니다. 왜냐하면 정적 초기화 순서로 실패 할 것이기 때문입니다.

관련 문제