[ROOT] RE:Here comes the next one...

From: Richard B. Kreckel (kreckel@ginac.de)
Date: Thu Jun 28 2001 - 15:54:25 MEST


Dear Masaharu,

On Thu, 28 Jun 2001, Masaharu Goto wrote:
> Thank you for reporting this. I've been trying to solve this
> for several days.  

Oops, I didn't expect this to be such a hard one.  Sorry.

> First, this kind of member template specialization was not
> supported by Cint.  So, it is obvious that this has a problem.

My example program has too little problems, too.  First, class `bar' is
missing a `public' section, second ABC::tinfo() must be virtualized.

> Second, when I comment out the part you pointed out in the
> dictionary, my g++ (RedHat6.2 Linux) still complains that there
> is no matching template.  I am trying to figure this out by reading
> ANSI/ISO C++, however, things are pretty ambiguous to me. 
> Could you point out which part of C++ standard explains about this 
> kind of template specialization? 

RedHat 6.2 comes with EGCS-1.1.2, right?  Maybe this old compiler is the
cause for some trouble.  The message that there is no matching template
usually occurs when you give a specilization like
    template<> inline bool is_exactly_a<foo>(const ABC & obj)
without having declared the general templated case yet:
    template <class T> inline bool is_exactly_a<foo>(const ABC & obj)
Unfortunately, I do not have access to such a thing but given said header
the following main routine works:

#include "test_see_below.h"
using namespace canig;
int main(void)
{
	ABC *f = new foo;
	ABC *b = new bar;
	if (is_exactly_a<foo>(*f)) {
		cout << "f points to a foo" << endl;
	}
	if (is_exactly_a<bar>(*f)) {
		cout << "f points to a bar" << endl;
	}
	if (is_exactly_a<foo>(*b)) {
		cout << "b points to a foo" << endl;
	}
	if (is_exactly_a<bar>(*b)) {
		cout << "b points to a bar" << endl;
	}
}

And it can easily be verified that the specialization is indeed being
called (as it should), at least on the following five compilers:

  SGI C++ on IRIX 6.5 (_COMPILER_VERSION==730)
  DEC C++ on Tru64 (__DECCXX_VER==60290024)
  GCC 2.95.x, GCC 2.96 (triple-cursed-RadHat-only-compiler) and GCC 3.0

I borrowed all this specialization stuff from Stroustrup's TC++PL 3rd
edition, section 13.5.  Section 14.7 [temp.spec] seems to be the right
pointer into the ISO standard.

Also, the fact that without the namespace Cint seems to eat this example
has led me to believe that it actually works.  Sadly, this doesn't seem to
be the case -- as I just realized...  It keeps telling me that the symbols
`is_exactly_a' and `foo' are not in the current scope.  (The latter one
bewilders me: `foo' should be okay here, since I can otherwise use this
class quite normally.)

>namespace canig {
>
>       class ABC {
>       public:
>               ABC() : tinfo_key(0) {}
>               unsigned tinfo() const { return tinfo_key; }
>       private:
>               const unsigned tinfo_key;
>       };
>
>       class foo : public ABC {
>       public:
>               foo() : tinfo_key(1) {}
>               unsigned tinfo() const { return tinfo_key; }
>       private:
>               const unsigned tinfo_key;
>       };
>       class bar : public ABC {
>               bar() : tinfo_key(2) {}
>               unsigned tinfo() const { return tinfo_key; }
>       private:
>               const unsigned tinfo_key;
>       };
>
>       template <class T>
>       inline bool is_exactly_a(const class ABC & obj)
>       {
>               const T _t; return _t.tinfo()==obj.tinfo();
>       }
>       // specialization:
>       template<> inline bool is_exactly_a<foo>(const ABC & obj)
>       {
>               return obj.tinfo()==1;
>       }
>
>}

Hope this helps
             -richy.
-- 
Richard B. Kreckel
<Richard.Kreckel@Uni-Mainz.DE>
<http://wwwthep.physik.uni-mainz.de/~kreckel/>



This archive was generated by hypermail 2b29 : Tue Jan 01 2002 - 17:50:50 MET