2

How can I specialize a class template so that the template parameters can be of type : a pointer to a particular class or a pointer to the derived class of that particular type? Is it possible to do it without using Boost?

Possible Duplicate of: C++ templates that accept only certain types

I just wanted to know whether the answer is same even if I am using a pointer to the instances .

Community
  • 1
  • 1
sajas
  • 1,599
  • 1
  • 17
  • 39
  • yes, you can use the standard library and c++ functionality – BЈовић Feb 04 '13 at 09:31
  • @BЈовић Template specialization that i have seen till now just specialized on pointer to a type. Like template class Class_Name. How can i say that T has to be of a particular user defined type? – sajas Feb 04 '13 at 09:37

2 Answers2

5

You could specialize your class for pointers and then use std::is_base_of with a static_assert:

template <typename T>
class foo;

template <typename T>
class foo<T*>
{
  static_assert(std::is_base_of<Base, T>::value, "Type is not a pointer to type derived from Base");
};

See it in action. Both std::is_base_of and static_assert are C++11 features so no Boost is required.

If for some reason you don't like static_assert, you could do it the enable_if way:

template <typename T, typename Enable = void>
class foo;

template <typename T>
class foo<T*, typename std::enable_if<is_base_of<Base, T>::value>::type>
{
  // ...
};
David G
  • 94,763
  • 41
  • 167
  • 253
Joseph Mansfield
  • 108,238
  • 20
  • 242
  • 324
  • Thanks for the information. I have one more doubt: is the statement: typename std::enable_if::value >::type* = 0 is used just for assertion ? – sajas Feb 04 '13 at 12:31
  • 1
    @sajas `enable_if` uses fancy features of the language to enforce assertion-style restraints on certain things. It can be used to enable different constructs under certain conditions. The example you've just given is for enabling a function templates, where you provide a dummy parameter with type `std::enable_if<...>::type*` defaulted to 0. The example I gave was for enabling a class specialization, where you provide a dummy template parameter in a similar way which is defaulted to `void`. – Joseph Mansfield Feb 04 '13 at 13:17
  • 1
    @sajas `enable_if` works by resulting in an invalid template instantiation when the condition is false. In particular, its member `type` is not defined if the condition is false. – Joseph Mansfield Feb 04 '13 at 13:20
1

A technique for having specializations based on some predicate instead of a pattern is to use an extra defaulted parameter.

template <typename T, bool = predicate<T>::value>
class foo {
    // here is the primary template
};

template <typename T>
class foo<T, true>  {
    // here is the specialization for when the predicate is true
};

All you need is a proper predicate. In this case, std::is_base_of seems to fit. There is a boost implementation of it too.

R. Martinho Fernandes
  • 228,013
  • 71
  • 433
  • 510
  • Thanks for the information. I have one more doubt: is the statement: typename std::enable_if::value >::type* = 0 is used just for assertion ? – sajas Feb 04 '13 at 12:30
  • @sehe Actually, I just wanted any one of them to reply to the question. Both the answers seems correct to me. – sajas Feb 04 '13 at 12:35
  • 1
    @sajas Thanks for your frank explanation. Please be aware that this is not received well by most answerers on SO. It is considered impolite. If you have further general questions (like this is), please search SO and optionally ask a new question should you fail to find it. – sehe Feb 04 '13 at 12:38
  • @sehe Sorry about that. Should I remove the comment? – sajas Feb 04 '13 at 12:43