(very) Simple Template Metaprogramming question

S

stdlib99

Hi,

I have a simple question regarding templates and meta programming.

I am going to try and work my way through the C++ Template
Metaprogramming, a book by David Abrahams and Aleksey Gurtovoy. I’m
not doing this because I want to be a Meta Programming guru (because a
lot of that stuff looks too crazy for use in the real world).

Rather I want to learn heavyweight templates and this is the only
hardcode template book that has questions and answers (on the web).

Anyway I have got as far as the first exercise. I have done the
exercise but I’m getting a compile error below.

I’m using Visual Studio 2005, but I’m sure its not a compiler problem
– its just I don’t understand what is going on.

The compile error is on the line (full code below):

const type_info& info1a = typeid(add_const_ref<int>::type);

where the compiler does not like the ::type in the call to typeid.

The error is :

error C2955: 'add_const_ref_impl<false>::type_' : use of class
template requires template argument list
see declaration of 'add_const_ref_impl<false>::type_'
see reference to class template instantiation 'add_const_ref<T>' being
compiled
with
[
T=int
]

I’m obviously don’t understand what is going on here. I would expect
that buy the time the compiler has done its meta programming magic
add_const_ref<int>::type would be a real type and I could pass it into
typeID, however that looks wrong. I think I'm misunderstanding
something fundermetal here so I'm posting.

So my question is why does this line fail to compile. Should I be able
to pass add_const_ref<int>::type into typeid()?

Thanks

stdlib

Ps. sorry if this is in the wrong group!


//====================================================

// This is an answer to they very first exercise in the
// C++ Template Metaprogramming book.
// Its the impl of a function add_const_ref function which add adds
converts a supplied type into
// a const ref to that type.

#include <boost/type_traits/is_reference.hpp>
#include <iostream>

template <bool is_ref> struct add_const_ref_impl
{};


template <>
struct add_const_ref_impl<false>
{
template<typename T>
struct type_
{
typedef const T& type;
};

};

template <>
struct add_const_ref_impl<true>
{
template<typename T>
struct type_
{
typedef T type;
};

};
//==========================================


template <class T>
struct add_const_ref
{
static const bool is_ref = boost::is_reference<T>::value;
typedef typename add_const_ref_impl<is_ref>::type_::type type;
};


int main()
{
const type_info& info1a = typeid(add_const_ref<int>::type); //
error C2955 here
const type_info& info2a = typeid(add_const_ref<int&>::type); //
error C2955 here

std::cout << info1a.name() << std::endl << info2a.name() <<
std::endl;

return 0;
}
//====================================================
 
B

bood

Hi,

I have a simple question regarding templates and meta programming.

I am going to try and work my way through the C++ Template
Metaprogramming, a book by David Abrahams and Aleksey Gurtovoy. I’m
not doing this because I want to be a Meta Programming guru (because a
lot of that stuff looks too crazy for use in the real world).

Rather I want to learn heavyweight templates and this is the only
hardcode template book that has questions and answers (on the web).

Anyway I have got as far as the first exercise.  I have done the
exercise but I’m getting a compile error below.

I’m using Visual Studio 2005, but I’m sure its not a compiler problem
– its just I don’t understand what is going on.

The compile error is on  the line (full code below):

  const type_info& info1a = typeid(add_const_ref<int>::type);

where the compiler does not like the ::type in the call to typeid.

The error is :

error C2955: 'add_const_ref_impl<false>::type_' : use of class
template requires template argument list
see declaration of 'add_const_ref_impl<false>::type_'
see reference to class template instantiation 'add_const_ref<T>' being
compiled
        with
        [
            T=int
        ]

I’m obviously don’t understand what is going on here. I would expect
that buy the time the compiler has done its meta programming magic
add_const_ref<int>::type would be a real type and I could pass it into
typeID, however that looks wrong. I think I'm misunderstanding
something fundermetal here so I'm posting.

So my question is why does this line fail to compile. Should I be able
to pass add_const_ref<int>::type into typeid()?

Thanks

stdlib

Ps. sorry if this is in the wrong group!

//====================================================

// This is an answer to they very first exercise in the
// C++ Template Metaprogramming book.
// Its the impl of a function add_const_ref function which add adds
converts a supplied type into
// a const ref to that type.

#include <boost/type_traits/is_reference.hpp>
#include <iostream>

template <bool is_ref> struct add_const_ref_impl
{};

template <>
struct add_const_ref_impl<false>
{
  template<typename T>
  struct type_
  {
    typedef const T& type;
  };

};

template <>
struct add_const_ref_impl<true>
{
  template<typename T>
  struct type_
  {
    typedef T type;
  };

};

//==========================================

template <class T>
struct add_const_ref
{
  static const bool is_ref = boost::is_reference<T>::value;
  typedef typename add_const_ref_impl<is_ref>::type_::type type;

};

int main()
{
  const type_info& info1a = typeid(add_const_ref<int>::type);  //
error C2955 here
  const type_info& info2a = typeid(add_const_ref<int&>::type); //
error C2955 here

  std::cout << info1a.name() << std::endl << info2a.name() <<
std::endl;

  return 0;}

//====================================================

I can see two things here:

First, when you reference add_const_ref_impl<is_ref>::type_::type in
add_const_ref, noticing add_const_ref_impl::type_ is also a template,
you should provide a template argument here too. This is what the
compiler complains about.

Second, in the statement typeid(add_const_ref<int>::type),
add_const_ref<int>::type will cause ambitious, you should add a
'typename' here:
typeid(typename add_const_ref<int>::type)
 
S

stdlib99

try this:



HTH,
jim

Hi,

Thanks to both of you for taking the time to reply.

The compile errors were indeed becase of the
missing template argument for type_<T>. Id did not have to use the
template Keyword
as VisualStudio 2008 was able to itendify the type_T<T> as a teample.

I as so made a mistake with the use of typeid():

I was expecting info1a.name() and info2a.name() to be different where
info2a.name would
be a const int&. But that is not the case as typeid() discards all the
const/ref info
so typeid(const int&) == typeid(int).
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,955
Messages
2,570,117
Members
46,705
Latest member
v_darius

Latest Threads

Top