2
template< int a, int b >
struct aa {
  template< int x, int y >
  struct att { int axx[ a + x ][ b + y ]; };
};   

struct b1 : public aa< 1, 2 > {
  typedef att< 1, 2 > x;
};

template< int q >
struct b2 : public aa< 12, q > {
    typedef att< 1, 2 > x;
}; 

b1 compiles without a problem (GCC 4.8), but b2 complains

error: 'att' does not name a type
typedef att< 1, 2 > x;
        ^   

why??

  • 1
    Try `using aa<1, 2>::att<1, 2>;` – 0x499602D2 Jan 19 '14 at 14:53
  • possible duplicate of [Derived template-class access to base-class member-data](http://stackoverflow.com/questions/1120833/derived-template-class-access-to-base-class-member-data) – juanchopanza Jan 19 '14 at 14:55
  • 2
    More like `typedef typename aa<12,q>::template att< 1, 2 > x;`. What a mouthful! See [this related question](http://stackoverflow.com/questions/610245/where-and-why-do-i-have-to-put-the-template-and-typename-keywords). – juanchopanza Jan 19 '14 at 14:58
  • @juanchopanza I don't think that's needed as `b1` and `b2` aren't templates.... :) – 0x499602D2 Jan 19 '14 at 14:59
  • @0x499602D2 `b2` is a template. – juanchopanza Jan 19 '14 at 14:59
  • @juanchopanza: make that an answer! But it is an ugly mouthful :) is there a good way to shorten it? My real code has ~ 30 such lines. (yes, it should be 'b2 cmplains') – Wouter van Ooijen Jan 19 '14 at 15:03
  • I think all the information is in the second link, which is a better duplicate than the first one. So I will abstain from answering. – juanchopanza Jan 19 '14 at 15:05

1 Answers1

1

Because non-dependent names such as att<1,2> are not looked up in dependent base classes (like aa<12,q>, which depends on q).

In the case of b1, the base class aa<1,2> is not a dependent base, so everything works fine. For b2, the easiest way is to write typename aa<12,q>::template att<1,2>.

For a relevant reference, see section 9.4.2 (Dependent Base Classes) in C++ Templates: The Complete Guide (Vandevoorde and Josuttis).

Stuart Golodetz
  • 19,132
  • 3
  • 45
  • 79