This is the mail archive of the mailing list for the libstdc++ project.

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: Char_traits (part 2+)

> To summarize my interpretation of the Standard:
> 1.	21.1.1/1 is not a definition of template class char_traits<>. It is a 
> statement of requirements – just like numerous similar tables in the 
> Standard.
> 2.	21.1.1/2 requires a declaration of template class char_traits<>. It is 
> not a definition either. It is also all we get.
> 3. and provide complete definitions of the explicit 
> specializations template<> struct char_traits<char> and template<> struct 
> char_traits<wchar_t> respectively. This suggests that the absence of a 
> complete definition in (2) is deliberate.
> 4.	It is not possible to provide a generic implementation of char_traits 
> that meets the requirements of 21.1.1/1 without imposing additional 
> requirements on the character type that are not mandated by the Standard.

Right. It's also not possible to do useful partial specializations for
char_traits due to only one template parameter.

The consensus seems to be that failing to provide a definition for
char_traits<_CharT> is strictly conforming, although not all that
friendly to users.

> Given these points, I consider any definition of template struct 
> char_traits<> to be an implementation defined extension. Since an extension 
> can be and do whatever it wants, we could just draw the line there and let 
> it go at that.

See current sources....

> Nevertheless, I had problems with the original char_traits implementation 
> because they were incorrect for most cases, and because of what I call the 
> “like a duck” problem. This is: if it looks like a ‘character traits’ class, 
> and calls itself a ‘character traits’ class, and is provided by the 
> implementation, then reasonable users can be excused when they think it is a 
> ‘character traits’ class – and for getting annoyed when they discover that 
> it is not correct.

Right. Why should libstdc++ get in the way? Also, it's still not clear
to me that people would be able to specialize if the generic template is
defined before their specializations are declared.

> The changes address only part of this problem – now attempts to use 
> char_traits<MyChar> will compile, but not link unless the user provides the 
> definitions. First, the Standard is clear that adding explicit 
> specializations of templates for built-in types to namespace std results in 
> undefined behavior (, so this doesn’t work for the expected 
> common cases. Additionally, the solution provides no useful functionality 
> for the user-defined types, so I do not see any point. In fact, it seems to 
> promise functionality that is NOT provided, so unless the requirement that 
> the users provide the function definitions is clearly spelled out somewhere, 
> I think it is actually more confusing than just going with only what the 
> Standard requires.

I guess I was thinking more of something like

typedef unsigned short unicode_type;
typedef unsigned char unsigned_type;

then doing

template<> struct std::char_traits<unicode_type>
// do the work

etc. Isn't this legal? Aren't these user-defined types, and thus allowed
to do the specialization of std::char_traits?

> (2) Let’s face it – the real issue is basic_string<>. Weirdo’s like me who 
> mess with clause 27 are rare and presumably should know what they are doing.

Given the number of bug reports in this area I suspect you'd be
surprised at the number of freaks doing this stuff. I certainly was.

> A.	Provide only what the Standard specifies without extensions. This has the 
> advantage that code will be more likely to be portable. It has the major 
> disadvantage that useful things like basic_string<unsigned char> will not 
> work.
> B.	Provide A plus implementation defined explicit specializations of the 
> other built-in character types. This is my preference. I think it is in 
> keeping with both the letter and the spirit of the Standard. It allows the 
> useful things like declaring a basic_string<unsigned char>, but prevents 
> accidental usage of more esoteric types.

Can "B" be provided as a generic skeletal stubs file that people fill in
for their own types (as above) instead of explicitly instantiated into
the for all the builtin types? I'd like to do this, and
also provide a similar template (or stubs) for the locale bits that need
to be done in order to work with streams.

If so, I consider this mostly a documentation issue. Here's to patches
that address it!

I'm curious: I don't feel like you addressed the issue of _Traits
ambiguity in some of the locale facets (where _Traits is not a template
parameter, but _Chart and _Iter (which itself has a _Traits param) are.)
This came up in regards to your original email, where you used
MyCharType, instead of a std::char_traits<MyCharType> specialization.
What do you think about this?

Do you agree that analysis was correct? That was the big issue I had
with the second round of char_traits cleanup that I did, actually.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]