2012-05-22 5 views
2

선택적 템플릿 매개 변수는 어떻게 구현합니까?선택적 템플릿 매개 변수를 구현하는 방법은 무엇입니까?

클래스 MyStruct<T1,T2,T3>을 갖고 싶습니다. 첫 번째 또는 처음 두 개의 매개 변수 만 사용할 수 있습니다. 이제 MyStruct<T1,T2,T3>을 처리하는 함수는 사용되지 않는 템플릿 매개 변수를 사용하여 올바르게 처리해야합니다.

예 :

이제
#include <iostream> 

template<class T1, class T2, class T3> 
struct MyStruct { 
    T1 t1; T2 t2; T3 t3; 
    MyStruct() {} 
    MyStruct(T1 const& t1_, T2 const& t2_, T3 const& t3_) 
    : t1(t1_), t2(t2_), t3(t3_) {} 
}; 

template<class T1, class T2, class T3> 
MyStruct<T1, T2, T3> myplus(MyStruct<T1, T2, T3> const& x, 
       MyStruct<T1, T2, T3> const& y) { 
    return MyStruct<T1, T2, T3>(x.t1 + y.t1, x.t2 + y.t2, x.t3 + y.t3); 
} 

int main() { 
    typedef MyStruct<int, double, std::string> Struct; 
    Struct x(2, 5.6, "bar"); 
    Struct y(6, 4.1, "foo"); 
    Struct result = myplus(x, y); 
    // (8, 9.7, "barfoo") 
    std::cout << result.t1 << "," << result.t2 << "," << result.t3; 
} 

나는 위의 main() 기능이 계속 작동하도록 코드를 변경하고 싶습니다,하지만 다음도 작동합니다 :

typedef MyStruct<std::string, int> Struct; 
// result: ("barfoo", 5) 
Struct result = myplus(Struct("bar", 2), Struct("foo", 3)); 

또는이 :

typedef MyStruct<int> Struct; 
// result: (5) 
Struct result = myplus(Struct(2), Struct(3)); 

boost::tuple은 비슷한 트릭을 사용합니다.을 사용할 수 있습니다., boost::tuple<A,B>, boost::tuple<A,B,C>,하지만 어떻게하는지 모르겠습니다.

당신은 의도적으로 "사용하지 않는"유형 만들 수

답변

3

: 나, 당신은 Boost.Tuple로, 기본 템플릿 매개 변수를 사용할 수 있습니다 Default을 입력하십시오.

+0

나는'Default()'를 반환하는'operator + (Default const & Default const &)'를 정의하면'plus()'함수가 작동 할 것이다. 좋은. – Frank

1

: C++ 11 (세게 방법이 더 복잡 옵션)에

namespace detail { struct unused { }; } 

template <typename T1, typename T2 = detail::unused, typename T3 = detai::unused> 
struct MyStruct 
{ 
    typedef T1 type1; 
    typedef T2 type2; 
    typedef T3 type3; 

    explicit MyStruct(type1 const & t1, 
         type2 const & t2 = type2(), 
         type3 const & t3 = type3()) 
    : x1(t1), x2(t2), x3(t3) 
    { } 

private: 
    type1 x1; 
    type2 x2; 
    type3 x3; 
}; 
+1

익명의 네임 스페이스에'Unused '를 넣는 것은 좋은 생각입니다.'MyStruct'를 헤더에 넣으면 다른 번역 단위가 다른'Unused'를 갖게되어 다른 MyStruct와 ODR을 위반했다. – ildjarn

+0

@ildjarn : 좋은 지적, 고정. –

3

당신이 사용하는 가변 인자 템플릿을 할 수 있습니다;

template<class T1, class T2 = Default, class T3 = Default> 

것은 당신이 어떤을 대체 값 수 : 내가 정확하게 당신을 얻을 경우 템플릿에 대한 기본 매개 변수를 전달 할 수 있어야한다

// boost/tuple/tuple/detail/tuple_basic.hpp 

// -- null_type -------------------------------------------------------- 
struct null_type {}; 

//... 

// - tuple forward declaration ----------------------------------------------- 
template < 
    class T0 = null_type, class T1 = null_type, class T2 = null_type, 
    class T3 = null_type, class T4 = null_type, class T5 = null_type, 
    class T6 = null_type, class T7 = null_type, class T8 = null_type, 
    class T9 = null_type> 
class tuple; 
+0

부스트 워드 프로세서가 '현재 버전은 0-10 요소가있는 튜플을 지원합니다.' 그래서 여기서 많은 마법이 일어나지 않습니다. 최대 한도까지 기본 값을 사용하는 하드 코딩 된 상한. – Falmarri

관련 문제