Templates / Compiler Error

E

Exits Funnel

Hello,

I've been tasked with porting some code which was written on Windows to
Linux (g++). The following is an excerpt of the code (which I've pared
down to the absolute minimum required to generate the error):

//Begin foo.cpp
template <typename BT>
struct chi_t { };

template<typename BT>
class B
{
public:
static chi_t<BT> sbhs;
};

struct PTB { };

class PTB_t : public B<PTB> { };


chi_t<PTB> PTB_t::sbhs("PTB" "PTB"); // This is line 15
//End foo.cpp

g++ has this to say:

foo.cpp:15: ISO C++ does not permit `B<PTB>::sbhs' to be defined as
`PTB_t::sbhs'

I have two questions:

1) What is line 15 trying to do? Even if g++ is correct to complain, it
compiles (presumably) on windows so it must mean something but I can't
'parse' it in my head. Is the 'sbhs("PTB" "PTB")' bit a ctor call?

2) Is there some obvious fix I can make to placate g++?

Thanks in advance.

-exits
 
A

Alf P. Steinbach

* Exits Funnel:
The following is an excerpt of the code (which I've pared
down to the absolute minimum required to generate the error):

//Begin foo.cpp
template <typename BT>
struct chi_t { };

template<typename BT>
class B
{
public:
static chi_t<BT> sbhs;
};

struct PTB { };

class PTB_t : public B<PTB> { };


chi_t<PTB> PTB_t::sbhs("PTB" "PTB"); // This is line 15
//End foo.cpp

g++ has this to say:

foo.cpp:15: ISO C++ does not permit `B<PTB>::sbhs' to be defined as
`PTB_t::sbhs'

I have two questions:

1) What is line 15 trying to do? Even if g++ is correct to complain, it
compiles (presumably) on windows so it must mean something but I can't
'parse' it in my head. Is the 'sbhs("PTB" "PTB")' bit a ctor call?

Yes (the argument is one literal string "PTBPTB"), but see below.

2) Is there some obvious fix I can make to placate g++?

The most obvious fix would be to provide a corresponding constructor.
When I do that Visual C++ reports "static data member cannot be
initialized via derived class". Changing PTB_t to B<PTB> fixes that.

However there's also some Very Bad Design here.

First, 'sbhs' is effectively a global variable which anyone can assign
to, with attendant problems.

Consider using any common implementation of the singleton pattern
instead, e.g.

template <typename BT>
struct chi_t { chi_t( char const [] ){} };

template<typename BT>
class B
{
public:
static chi_t<BT> sbhs();
};

struct PTB { };

class PTB_t : public B<PTB> { };

template<>
chi_t<PTB> B<PTB>::sbhs()
{
static chi_t<PTB> theInstance( "PTBPTB" );
return theInstance;
}

int main()
{
PTB_t o;
}

Second, the names are awful. Recommendations: (1) don't use all
uppercase for anything but macros, and (2) use descriptive names, both
for the types and for the 'sbhs' function (what on Earth is it?). If or
when you follow these recommendations you will probably discover that
the whole shebang is some mathematician's spaghetti design which could
be infinitely simplified. And then rewriting this from scratch...
 
E

Exits Funnel

2) Is there some obvious fix I can make to placate g++?
The most obvious fix would be to provide a corresponding constructor.

Actually, the ctor did exist of course in the actual code but I hadn't
included it in the pared down version because it wasn't clear to me then
(though is is now, thanks to your helpful reply) that the code in
question was a ctor call. Adding the ctor though to my sample code in
itself didn't change the error generated by g++.
When I do that Visual C++ reports "static data member cannot be
initialized via derived class".

Just out of curiousity, what version of Visual C++? The code in
question was written under 7.1 and I beleive compiles without error.

Changing PTB_t to B<PTB> fixes that.

Yes, that change seems to satisfy g++. Thanks!
However there's also some Very Bad Design here.

First, 'sbhs' is effectively a global variable which anyone can assign
to, with attendant problems.

Consider using any common implementation of the singleton pattern
instead, e.g.

template <typename BT>
struct chi_t { chi_t( char const [] ){} };

template<typename BT>
class B
{
public:
static chi_t<BT> sbhs();
};

struct PTB { };

class PTB_t : public B<PTB> { };

template<>
chi_t<PTB> B<PTB>::sbhs()
{
static chi_t<PTB> theInstance( "PTBPTB" );
return theInstance;
}

int main()
{
PTB_t o;
}

I'm sure this is a good suggestion.
Second, the names are awful. Recommendations: (1) don't use all
uppercase for anything but macros, and (2) use descriptive names, both
for the types and for the 'sbhs' function (what on Earth is it?). If or
when you follow these recommendations you will probably discover that
the whole shebang is some mathematician's spaghetti design which could
be infinitely simplified. And then rewriting this from scratch...

Actually, the names in the actual code are much more descriptive. I
just used query-replace to simplify them for posting to USENET. Thanks
again for all your help.

-exits
 
M

Mike Wahler

Actually, the names in the actual code are much more descriptive. I
just used query-replace to simplify them for posting to USENET.

IMO you wasted your time. When you use cryptic, meaningless names,
that doesn't 'simplify' anything, it makes it clumsy to follow (thus
takes longer to understand). Try to make your code read similar to
a 'natural' language such as English, e.g:

if(sum < 0) /* there's a reason the keyword is 'if' :) */
display_error();

But of course, execessively long names cause the same problem
from the 'other direction'. Easily recognizable abbreviations[*]
can help with striking a good balance. The goal should be to
make the code readable, quickly and easily, by you, and especially
by others. Source code is more for communication between people
than between people and machines.

[*] Why is 'abbreviation' such a long word? :)

-Mike
 

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

Forum statistics

Threads
473,755
Messages
2,569,537
Members
45,020
Latest member
GenesisGai

Latest Threads

Top