Topic: Re:iosfwd and coding style
Author: Alessandro Vesely <mc6192@mclink.it>
Date: 1997/01/06 Raw View
James Kanze answered to me:
>> My question is: does anybody seriously think that the following should
>> be considered good programming style?
>>
>> int_type c = some_get_function();
>> if ( traits_type::eq_int_type( c, traits_type::to_int_type( '?')))
>> // ...
>
>It depends on what you are trying to do. At the application level, for
>example, I cannot think of an occasion where it would occur.
Parsing. It is difficult to parse an expression by just comparing
(w)strings, unless the grammar requires white space between any two
tokens. Thus, parsing requires comparing character objects one at a
time.
>> I mean, why are we are using a language with operators overloading if
>> we cannot write
>>
>> if ( c == '?')
>> // ...
>>
>> I know that traits 'only' need to be used when writing templates that
>> somehow deal with characters. Unfortunately, the vast majority of classes
>> and functions happen to somehow deal with characters. Shouldn't they be
>> templatized as well? And what coding style should be recommended?
>
>With regards to characters, IMHO, an application will choose ONE (and
>only one) character type for internal use, normally, wstring, I
>imagine. The only case where other character types may appear will be
>in the iostream classes; a well designed implementation should be able
>to convert on the fly. Note, for example, that handling multi-byte
>codes internally is extremely difficult.
This is certainly true for most applications. However, it is not true
for most libraries. If only one character type makes sense, what is
the other type there for? I mean char versus wchar_t (multi-byte
conversion is different.) Since all the characters I use can be
represented by a char, I usually don't use wchar_t. I fear using it
could nearly double the size of memory and disk resources my programs
use. I may be wrong, but still I wouldn't use a class that could only
handle wchar_t. Therefore, a library class that sticks on ONE
character type is less (re) usable than a template. Two library
classes that happen to work with different character types are not
compatible. This is true regardless of the library being low level,
high level or anywhere in between: the two classes cannot communicate
text to each other. So, the day a change my mind I have to throw away
any otherwise reusable class I've written until then.
Expression as the one above are needed in any reusable library class
that parses text. Some of the most complex and interesting
applications need parsing text. Complex applications are likely to be
built out of components. After all, reusing software and assembling
components have always been key issues in OO programming in general
and in C++ in particular. Hence, it is somewhat misleading to deem
only the C++ I/O Library to have such reusability requirements
(again, except for multi-byte conversion.)
>> IMHO, iosfwd reveals either a serious weakness in the predefined types
>> or a fundamental flaw in the C++ I/O Library design, depending on the
>> point of view.
>
>IMHO, iosfwd is a very good solution to a problem in the language, that
>you cannot forward declare a template instantiation as a class. The
>problem in the language is linked to implementation difficulties; while
>there are probably solutions, they are not obvious.
>From a technical standpoint, I agree iosfwd is a good solution. (Even
if it doesn't cover all the ctype/string functions available in the C
Library and the ones covered introduced new names.) However, iosfwd
being good, or very good, does only show up the magnitude of another
problem.
Let me try to express that problem more clearly, by sketching a
tentative solution. Ehm, *two* tentative solutions, depending on the
point of view.
1) The predefined types. Introduce a new type, say, nchar_t (for
narrow), and specify that the int type should contain at least one bit
more than either nchar_t or wchar_t. Further, specify that integer
promotion of any Xchar_t will not be sign extended. This won't
provide for strings of maps, but covers all practical cases. The
language will have to be amended again to introduce new types as
needed, e.g., kchar_t (for Klingon :-)
2) The C++ I/O Library. Mandate the use of a buffer for any streambuf
derived class. Functions like sbumpc or sputc will not return the
character but the result code, e.g. ios::iostate. If the code is
ios::goodbit, the character will be in the buffer (a buffer could be
as small as a single character, member of streambuf). This doen't
provide for any int_type at all. Existing functions, e.g. isalpha,
should be overloaded on char and wchar_t, not take nor return an int.
Those two 'solutions', at least the way they are expressed above, are
not intended as actual suggestions. But as a mean to express what I
consider to be a problem.
I did consider writing my own class char, with overloaded operators,
but then I would have difficulties and inefficiencies in using it for
I/O with predefined type char. As I see it, the root of the problem
is that EOF, or traits_type::eof(), compares equal to char(255),
because of integer promotion. A bug most of us went through. From
that perspective, iosfwd looks like an excessive remedy that tends to
hide the problem rather than solving it: "How to express that gotcha
in terms of an unspecified type".
Ciao
Ale
---
[ comp.std.c++ is moderated. To submit articles: Try just posting with your
newsreader. If that fails, use mailto:std-c++@ncar.ucar.edu
comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
Comments? mailto:std-c++-request@ncar.ucar.edu
]