Reputation: 4506
In the gcc library, the template basic_stringbuf is derived from basic_streambuf. In the base class basic_streambuf, the type names, such as char_type, traits_type, are already declared. Why they are duplicated declared in the child class basic_stringbuf?
The related code is pasted below.
// c++/4.2.1/streambuf
template<typename _CharT, typename _Traits>
class basic_streambuf
{
public:
//@{
/**
* These are standard types. They permit a standardized way of
* referring to names of (or names dependant on) the template
* parameters, which are specific to the implementation.
*/
typedef _CharT char_type;
typedef _Traits traits_type;
typedef typename traits_type::int_type int_type;
typedef typename traits_type::pos_type pos_type;
typedef typename traits_type::off_type off_type;
//@}
//@{
/**
* @if maint
* This is a non-standard type.
* @endif
*/
typedef basic_streambuf<char_type, traits_type> __streambuf_type;
//@}
…
};
// c++/4.2.1/sstream
template<typename _CharT, typename _Traits, typename _Alloc>
class basic_stringbuf : public basic_streambuf<_CharT, _Traits>
{
public:
// Types:
typedef _CharT char_type;
typedef _Traits traits_type;
// _GLIBCXX_RESOLVE_LIB_DEFECTS
// 251. basic_stringbuf missing allocator_type
typedef _Alloc allocator_type;
typedef typename traits_type::int_type int_type;
typedef typename traits_type::pos_type pos_type;
typedef typename traits_type::off_type off_type;
typedef basic_streambuf<char_type, traits_type> __streambuf_type;
typedef basic_string<char_type, _Traits, _Alloc> __string_type;
typedef typename __string_type::size_type __size_type;
…
};
Update:
The char_type is already declared in the parent class as a public member. The child class can use it directly. My question is why not gcc implements the basic_stringbuf as below
template<typename _CharT, typename _Traits, typename _Alloc>
class basic_stringbuf : public basic_streambuf<_CharT, _Traits>
{
public:
// Types:
//typedef _CharT char_type;
//typedef _Traits traits_type;
// _GLIBCXX_RESOLVE_LIB_DEFECTS
// 251. basic_stringbuf missing allocator_type
typedef _Alloc allocator_type;
//typedef typename traits_type::int_type int_type;
//typedef typename traits_type::pos_type pos_type;
//typedef typename traits_type::off_type off_type;
typedef basic_streambuf<char_type, traits_type> __streambuf_type;
typedef basic_string<char_type, _Traits, _Alloc> __string_type;
typedef typename __string_type::size_type __size_type;
…
};
EDIT:
Thanks K-ballo. I think your answer makes sense. I tried the code below. The type name char_type can't be used in the child class.
template<typename _CharT>
class Base
{
public:
typedef _CharT char_type;
};
template<typename _CharT>
class Child : public Base<_CharT>
{
private:
char_type _M_Data; // FAIL: Unknown type name 'char_type'
};
Upvotes: 4
Views: 276
Reputation: 81349
Have you tried doing that? The base class basic_streambuf<_CharT, _Traits>
is a dependent type, the compiler won't know what specialization of basic_streambuf
(if any) will this base be until the actual type is instantiated. Because of that, definitions for the base class are not visible in the derived class. To make a type declared in a dependent base class visible one usually does typedef typename base_class::some_type some_type;
, gcc just decided to redefine them again just as the base does.
It reduces to the fact that char_type
, though declared in the parent class as a public member, cannot be used directly by the child class. It would have to use it as
typename basic_streambuf< _CharT, _Traits >::char_type
Upvotes: 2