Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C++ > Constraining a template class argument to a derived class of base

Reply
Thread Tools

Constraining a template class argument to a derived class of base

 
 
amkg
Guest
Posts: n/a
 
      11-05-2008
Hello world,

I'm trying to figure out some way to constrain a template class
argument for a member function definition, such that the template
class argument must, totally, absolutely be a derived class of a
certain base class.

My current solution is:

class Base {
// etc..
};

class BaseHolder {
//etc
public:
template<class T>
T* make(void) {
/*This one!*/
Base* _check_derived_from_Base_ =
static_cast<Base*>((T*) 0);
return new(alloc(sizeof(T))) T();
}
};

It *seems* to work, but I think it's kind of hackish. Is there a
better, standards-defined way where I can specify that the class T in
the template should derive from "Base"?

Sincerely,
AmkG
 
Reply With Quote
 
 
 
 
Michael DOUBEZ
Guest
Posts: n/a
 
      11-05-2008
amkg a écrit :
> Hello world,
>
> I'm trying to figure out some way to constrain a template class
> argument for a member function definition, such that the template
> class argument must, totally, absolutely be a derived class of a
> certain base class.
>
> My current solution is:
>
> class Base {
> // etc..
> };
>
> class BaseHolder {
> //etc
> public:
> template<class T>
> T* make(void) {
> /*This one!*/
> Base* _check_derived_from_Base_ =
> static_cast<Base*>((T*) 0);
> return new(alloc(sizeof(T))) T();
> }
> };
>
> It *seems* to work, but I think it's kind of hackish. Is there a
> better, standards-defined way where I can specify that the class T in
> the template should derive from "Base"?


Use boost static_assert and is_derived:
BOOST_STATIC_ASSERT(is_derived(T,Base));

If you don't want boost, the usual way to make the template
instantiation fail if a conversion cannot occur:

template <class T, class B>
struct assert_derived
{
//declare static constant to avoid T default construtible
static const T x;

//convert type to its pointer
template <class X>
static X* to_pointer(X const&);

//if can convert
static char convert_to_base(B const*);

//this fail if cannot convert to pointer
static const bool test=sizeof(convert_to_base(to_pointer(x)));
};


Then in your code:
assert_derived<T,Base>();

But the error code generated if far from meaningful.

--
Michael
 
Reply With Quote
 
 
 
 
amkg
Guest
Posts: n/a
 
      11-05-2008
On Nov 6, 12:09*am, Michael DOUBEZ <(E-Mail Removed)> wrote:
> amkg a écrit :
>
>
>
> > Hello world,

>
> > I'm trying to figure out some way to constrain a template class
> > argument for a member function definition, such that the template
> > class argument must, totally, absolutely be a derived class of a
> > certain base class.

>
> > My current solution is:

>
> > class Base {
> > // etc..
> > };

>
> > class BaseHolder {
> > //etc
> > public:
> > * * template<class T>
> > * * T* make(void) {
> > * * * * /*This one!*/
> > * * * * Base* _check_derived_from_Base_ =
> > * * * * * * static_cast<Base*>((T*) 0);
> > * * * * return new(alloc(sizeof(T))) T();
> > * * }
> > };

>
> > It *seems* to work, but I think it's kind of hackish. *Is there a
> > better, standards-defined way where I can specify that the class T in
> > the template should derive from "Base"?

>
> Use boost static_assert and is_derived:
> BOOST_STATIC_ASSERT(is_derived(T,Base));
>
> If you don't want boost, the usual way to make the template
> instantiation fail if a conversion cannot occur:
>
> template <class T, class B>
> struct assert_derived
> {
> * * *//declare static constant to avoid T default construtible
> * * *static const T x;
>
> * * *//convert type to its pointer
> * * *template <class X>
> * * * * *static X* to_pointer(X const&);
>
> * * *//if can convert
> * * *static char convert_to_base(B const*);
>
> * * *//this fail if cannot convert to pointer
> * * *static const bool test=sizeof(convert_to_base(to_pointer(x)));
>
> };
>
> Then in your code:
> assert_derived<T,Base>();
>
> But the error code generated if far from meaningful.
>
> --
> Michael


Thanks, I'll check out that template. Currently the hack I posted
gives a reasonable error in gcc - invalid static_cast from type ‘Bar*’
to type ‘Base*'. If the error code of that template is worse, I'll
stick with my hack I guess.
 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
r H2 deduce deduce template argument of a template class inheritingfrom a non template base? nguillot C++ 5 03-08-2009 05:56 PM
Help getting to a derived class template given a pointer to a no-template base class chris.kemmerer@att.net C++ 7 09-28-2007 01:55 AM
Derived::Derived(const Base&) and Derived& operator=(const Base&) developereo@hotmail.com C++ 1 05-23-2007 01:44 PM
Derived::Derived(const Base&) and Derived& operator=(const Base&) developereo@hotmail.com C++ 1 05-23-2007 12:07 AM
Re: template class derived from non-template base class Matt Graham C++ 0 07-21-2003 09:02 PM



Advertisments