This is the mail archive of the
libstdc++@gcc.gnu.org
mailing list for the libstdc++ project.
Re: user-defined types and basic_string
- From: Gabriel Dos Reis <gdr at integrable-solutions dot net>
- To: Benjamin Kosnik <bkoz at redhat dot com>
- Cc: libstdc++ at gcc dot gnu dot org
- Date: 23 Aug 2002 20:03:25 +0200
- Subject: Re: user-defined types and basic_string
- Organization: CodeSourcery, LLC
- References: <200208231731.g7NHV7Q02241@fillmore.constant.com>
Benjamin Kosnik <bkoz@redhat.com> writes:
| Here's an example of how to do a portable, standards-conformant string
| class with underlying type of unsigned short. This also works for
| things like unsigned char. Comments welcome.
Thanks for posting this.
| // Assumes pass-by-value is ok, --> simple type, probably builtin.
| // If this is not the case, don't have operator and have specific operators.
| struct character
| {
| typedef unsigned short value_type;
| value_type value;
|
| explicit character(): value(value_type()) { }
| character(const value_type ch): value(ch) { }
User-defined constructors are not permitted in PODs.
I think we don't really need the conversion function.
To the above should just read
struct character
{
unsigned short value;
};
Or, I think we could just put in a template surrogate for fundamental
types:
template<typename _Tp>
struct character
{
T value;
};
along with the two functions:
template<typename T>
inline bool
operator==(character<T> lhs, character<T> rhs)
{ return lhs.value == rhs.value; }
template<typename T>
inline bool
operator<(character<T> lhs, character<T> rhs)
{ return lhs.value < rhs.value; }
| // Provide std::char_traits specialization.
| namespace std
| {
| template<>
| struct char_traits<character>
| {
| typedef character char_type;
|
| // NB: this type should be bigger than char_type, so as to
| // properly hold EOF values in addition to the full range of
| // char_type values.
| typedef unsigned long int_type;
This makes the assumption that range(unsigned long) is a strict
superset of range(unsigned short). If we were going to assume that,
why not just use "int" as int_type?
| static char_type
| to_char_type(const int_type& __c)
| { return char_type(__c); }
char_type __r = { __c };
return __r;
| static int_type
| to_int_type(const char_type& __c) { return int_type(__c); }
{ return int_type(__c.value); }
>From your yesterday mail, I thought you were talking of a generic way
to define customization points of char_traits for users.
Actually, I'm not convinced that we should make a big deal about
defining a specialization for std::char_traits<>. Defining such a
specialization just amonts to define a trait class in one's own
namespace, but then there is no need to wrap the fundamental types in
a struct. Thoughts?
-- Gaby