3

here is what I need to do :

#include <iostream>                                                                                                                                                                                              

using namespace std;

class A
{
    public :
    virtual void fa() = 0;
};

template <typename type>
class B : public A
{
    protected :
    int v_b;
};

template <typename type>
class C : public B<type>
{
    public :
    void fa()
    {
        // whatever action that try to access v_b
        cout << "v_b = " << v_b << endl;
    }
};

int main()
{
    C<int> toto;
    toto.fa();
    return 0;
}

and here is g++ output :

test.cpp: In member function ‘void C<type>::fa()’:
test.cpp:25:29: error: ‘v_b’ was not declared in this scope

In my understanding, v_b is a protected member of B and is therefore accessible in C. A and B are both abstract classes, and I need to override the f_a() method of A in class C in order to instanciate it. Since the compiler is telling me this

test.cpp: In member function ‘void C<type>::fa()’:

and NOT

‘void A::fa()’:

i don't get why the v_b variable is not present in the scope. Is this a problem in the way I use templates?

Can anyone help me out on that one ?

thx

edit :

I tryed to use this->v_b or B<type>::v_b as suggested here and it worked fine ! thx for your help

Community
  • 1
  • 1
gameboo
  • 93
  • 1
  • 10

1 Answers1

3

In the expression:

    cout << "v_b = " << v_b << endl;

v_b is a non-dependent expression (i.e. it does not look like it depends on the template arguments. For a non-dependent expression the first phase lookup must resolve the symbol, and it will do so by looking only in non-dependent contexts. This does not include a templated base (as it does depend on the type argument). The simple fix is to qualify the call with this:

    cout << "v_b = " << this->v_b << endl;

Now it is a dependent expression (this which clearly depends on the instantiating type), and lookup is delayed to the second phase where the type is substituted and the bases can be checked.

David Rodríguez - dribeas
  • 204,818
  • 23
  • 294
  • 489
  • thanks for the fast answer, even faster than my edit ! I tried to look in that direction but I still have issues that I don't understand. Would you please have a look at what happened ? thanks a lot for your help – gameboo Jun 29 '12 at 22:58
  • no you're right ! when trying to test different solutions, as desperate as it may look, I left a "template class C : public B {" when i made my edit ! Thx for pointing this out ! I can sleep now ;) – gameboo Jun 30 '12 at 12:38