Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Is std::wcout really required?

3 views
Skip to first unread message

Amit Kumar

unread,
Jun 27, 2009, 2:04:30 PM6/27/09
to
Output of all the four statements are the same on Visual studio:

std::cout << "Hello\n";
std::wcout << "Hello\n";
std::cout << L"Hello\n";
std::wcout << L"Hello\n";

If cout and wcout can handle both char strings and wide char strings
then why do we need wcout?

Sam

unread,
Jun 27, 2009, 2:52:32 PM6/27/09
to
Amit Kumar writes:

You have assumed that you know what kind of output you're going to get from
the above code fragments.

Why don't you try running the above code fragments, and see what happens.
You will answer your own question.

Alf P. Steinbach

unread,
Jun 27, 2009, 4:17:23 PM6/27/09
to
* Amit Kumar:

By default std::cout can't handle wide text (see Sam's reply else-thread).


> then why do we need wcout?

We don't, not in the form it has (translating to narrow characters). It's an
abomination, a monstrosity, a completely redundant appendix in the acidic
digestive system of C++, the system which end-product is... well, u know. ;-)

And e.g. MinGW g++ 3.4.5 for Windows does not even implement it. :-)


Cheers & hth.,

- Alf

--
Due to hosting requirements I need visits to <url: http://alfps.izfree.com/>.
No ads, and there is some C++ stuff! :-) Just going there is good. Linking
to it is even better! Thanks in advance!

Developer

unread,
Jun 27, 2009, 10:48:34 PM6/27/09
to
They are not exactly the same

--
http://contract-developer.dyndns.biz

"Amit Kumar" <amitkum...@gmail.com> wrote in message
news:bd4fc074-0817-480c...@f19g2000yqo.googlegroups.com...

Thomas Matthews

unread,
Jun 28, 2009, 4:05:13 AM6/28/09
to

Yes, wcout is required since changing the functionality of cout
would screw up a bunch of legacy programs.

However, there is nothing stopping _you_ from overloading
cout to perform the way _you_ think it should.

--
Thomas Matthews

C++ newsgroup welcome message:
http://www.slack.net/~shiva/welcome.txt
C++ Faq: http://www.parashift.com/c++-faq-lite
C Faq: http://www.eskimo.com/~scs/c-faq/top.html
alt.comp.lang.learn.c-c++ faq:
http://www.comeaucomputing.com/learn/faq/
Other sites:
http://www.josuttis.com -- C++ STL Library book
http://www.sgi.com/tech/stl -- Standard Template Library

Bo Persson

unread,
Jun 28, 2009, 4:24:51 AM6/28/09
to

No, the results are not the same. Outputting a wide string to cout
differs from the others.

On recent versions of Windows, the question is "Why do we need cout,
when wcout works for both narrow and wide strings?".

On other systems, the question might be different.


Bo Persson


Donkey Hottie

unread,
Jun 28, 2009, 10:32:34 AM6/28/09
to
"Bo Persson" <b...@gmb.dk> wrote in message
news:7aonmaF...@mid.individual.net

>
> On recent versions of Windows, the question is "Why do we
> need cout, when wcout works for both narrow and wide
> strings?".
> On other systems, the question might be different.
>

So why the Windows implementation defines a new wcout, and not re-define
cout in the first place?


Bo Persson

unread,
Jun 28, 2009, 11:23:56 AM6/28/09
to

It is not new, they are both in the language standard. It is just that
as newer Windows versions internally uses wchar_t for characters,
wcout is a better match.


Bo Persson


Alf P. Steinbach

unread,
Jun 28, 2009, 3:14:00 PM6/28/09
to
* Bo Persson:

I'm not sure I understand what you're talking about.

Could you sort of elaborate?

James Kanze

unread,
Jun 28, 2009, 4:17:27 PM6/28/09
to
On Jun 27, 10:17 pm, "Alf P. Steinbach" <al...@start.no> wrote:
> * Amit Kumar:

> > Output of all the four statements are the same on Visual
> > studio:

> > std::cout << "Hello\n";
> > std::wcout << "Hello\n";
> > std::cout << L"Hello\n";
> > std::wcout << L"Hello\n";

> > If cout and wcout can handle both char strings and wide char
> > strings

> By default std::cout can't handle wide text (see Sam's reply
> else-thread).

Sam didn't make it clear what the problem is. In a conforming
implementation, you can't output wide character text to
std::cout, period. It shouldn't compile.

> > then why do we need wcout?

> We don't, not in the form it has (translating to narrow
> characters). It's an abomination, a monstrosity, a completely
> redundant appendix in the acidic digestive system of C++, the
> system which end-product is... well, u know. ;-)

I'm not sure what your point is. We definitely do need
something to output wchar_t, translating it to bytes as needed
(in a locale dependant manner).

> And e.g. MinGW g++ 3.4.5 for Windows does not even implement
> it. :-)

G++ is very, very behind with regards to internationalization.
At least on platforms other than Linux.

--
James Kanze (GABI Software) email:james...@gmail.com
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34

Alf P. Steinbach

unread,
Jun 28, 2009, 4:58:16 PM6/28/09
to
* James Kanze:

> On Jun 27, 10:17 pm, "Alf P. Steinbach" <al...@start.no> wrote:
>> * Amit Kumar:
>
>>> Output of all the four statements are the same on Visual
>>> studio:
>
>>> std::cout << "Hello\n";
>>> std::wcout << "Hello\n";
>>> std::cout << L"Hello\n";
>>> std::wcout << L"Hello\n";
>
>>> If cout and wcout can handle both char strings and wide char
>>> strings
>
>> By default std::cout can't handle wide text (see Sam's reply
>> else-thread).
>
> Sam didn't make it clear what the problem is. In a conforming
> implementation, you can't output wide character text to
> std::cout, period.

Of course you can. Or, perhaps not you you. But anyone else. :-)


> It shouldn't compile.

Oh, well. I kindof agree with that. Unfortunately, compilers don't.


>>> then why do we need wcout?
>
>> We don't, not in the form it has (translating to narrow
>> characters). It's an abomination, a monstrosity, a completely
>> redundant appendix in the acidic digestive system of C++, the
>> system which end-product is... well, u know. ;-)
>
> I'm not sure what your point is.

Mostly that wcout is an abomination, a monstrosity, so on. Given that anyone
would want to use std::cout, then that's where conversion from various types to
sequences of bytes is handled. There's no reason to have a separate stream for
just one special small set of types; it's so stupid that it isn't even wrong.


> We definitely do need
> something to output wchar_t, translating it to bytes as needed
> (in a locale dependant manner).
>
>> And e.g. MinGW g++ 3.4.5 for Windows does not even implement
>> it. :-)
>
> G++ is very, very behind with regards to internationalization.
> At least on platforms other than Linux.

Yah.

James Kanze

unread,
Jun 29, 2009, 4:37:29 AM6/29/09
to
On Jun 28, 10:58 pm, "Alf P. Steinbach" <al...@start.no> wrote:
> * James Kanze:
> > On Jun 27, 10:17 pm, "Alf P. Steinbach" <al...@start.no> wrote:
> >> * Amit Kumar:

> >>> Output of all the four statements are the same on Visual
> >>> studio:

> >>> std::cout << "Hello\n";
> >>> std::wcout << "Hello\n";
> >>> std::cout << L"Hello\n";
> >>> std::wcout << L"Hello\n";

> >>> If cout and wcout can handle both char strings and wide char
> >>> strings

> >> By default std::cout can't handle wide text (see Sam's reply
> >> else-thread).

> > Sam didn't make it clear what the problem is. In a conforming
> > implementation, you can't output wide character text to
> > std::cout, period.

> Of course you can. Or, perhaps not you you. But anyone else.
> :-)

Really. How?

> > It shouldn't compile.

> Oh, well. I kindof agree with that. Unfortunately, compilers don't.

Actually, I was wrong there. It should compile, but once
compiled, it doesn't do what you want: when you pass a wchar_t*
to std::cout, you get an implicit conversion to void*, and it
outputs the address of the string, not the contents. At least,
according to the standard, and the three compilers I have ready
access too (g++, Sun CC and VC++).

> >>> then why do we need wcout?

> >> We don't, not in the form it has (translating to narrow
> >> characters). It's an abomination, a monstrosity, a completely
> >> redundant appendix in the acidic digestive system of C++, the
> >> system which end-product is... well, u know. ;-)

> > I'm not sure what your point is.

> Mostly that wcout is an abomination, a monstrosity, so on.

I know. You don't like iostream. For at least certain aspects
of the wide character streams, I agree with you. But that's
neither here nor there. We need something to do the job.

> Given that anyone would want to use std::cout, then that's
> where conversion from various types to sequences of bytes is
> handled. There's no reason to have a separate stream for just
> one special small set of types; it's so stupid that it isn't
> even wrong.

I fail to understand what you're saying. The wide character
streams don't deal in sequences of bytes at all; they deal in
sequences of wchar_t. And while the standard says that wchar_t
can be a char (in which case, wide character streams are rather
useless), that's not the case on any of the machines I have
ready access to.

Alf P. Steinbach

unread,
Jun 29, 2009, 5:22:24 AM6/29/09
to
* James Kanze:
> On Jun 28, 10:58 pm, "Alf P. Steinbach" <al...@start.no> wrote:
>> * James Kanze:
>>> On Jun 27, 10:17 pm, "Alf P. Steinbach" <al...@start.no> wrote:
>>>> * Amit Kumar:
>
>>>>> Output of all the four statements are the same on Visual
>>>>> studio:
>
>>>>> std::cout << "Hello\n";
>>>>> std::wcout << "Hello\n";
>>>>> std::cout << L"Hello\n";
>>>>> std::wcout << L"Hello\n";
>
>>>>> If cout and wcout can handle both char strings and wide char
>>>>> strings
>
>>>> By default std::cout can't handle wide text (see Sam's reply
>>>> else-thread).
>
>>> Sam didn't make it clear what the problem is. In a conforming
>>> implementation, you can't output wide character text to
>>> std::cout, period.
>
>> Of course you can. Or, perhaps not you you. But anyone else.
>> :-)
>
> Really. How?

Depends on what you mean by 'output'.

If you mean the act of passing e.g. a wchar_t const* as argument and getting
some byte sequence as result, then you have that without doing anything, which
is part of what the "you can" means, but the result is not very useful, which is
what the "can't handle" meant -- on the way you changed the context a little.

If you want a more sensible conversion to byte sequence define an operator<<
overload, for example.


>>> It shouldn't compile.
>
>> Oh, well. I kindof agree with that. Unfortunately, compilers don't.
>
> Actually, I was wrong there. It should compile, but once
> compiled, it doesn't do what you want: when you pass a wchar_t*
> to std::cout, you get an implicit conversion to void*, and it
> outputs the address of the string, not the contents. At least,
> according to the standard, and the three compilers I have ready
> access too (g++, Sun CC and VC++).
>
>>>>> then why do we need wcout?
>
>>>> We don't, not in the form it has (translating to narrow
>>>> characters). It's an abomination, a monstrosity, a completely
>>>> redundant appendix in the acidic digestive system of C++, the
>>>> system which end-product is... well, u know. ;-)
>
>>> I'm not sure what your point is.
>
>> Mostly that wcout is an abomination, a monstrosity, so on.
>
> I know. You don't like iostream. For at least certain aspects
> of the wide character streams, I agree with you. But that's
> neither here nor there. We need something to do the job.

Yes, and it seems the error of the committee on this one was to take something
rather silly, look at it, "hey, this is something", and concluding, from the
earlier established need for something, that therefore the silly was needed.


>> Given that anyone would want to use std::cout, then that's
>> where conversion from various types to sequences of bytes is
>> handled. There's no reason to have a separate stream for just
>> one special small set of types; it's so stupid that it isn't
>> even wrong.
>
> I fail to understand what you're saying. The wide character
> streams don't deal in sequences of bytes at all; they deal in
> sequences of wchar_t.

Nope, the appearance that they deal in wchar_t sequences is just appearance,
cosmetics, complication. It may have been the original intention, who knows. But
what they /do/ is to convert to byte (char) sequences, the same as the narrow
streams, and with the same destinations.

So why should one have to deal with 2 streams converting two slightly different
sets of types to char sequences on standard output, instead of just 1 stream
converting any of those types to char sequences on standard output?

There is no answer to that, for the design is just meaningless.

And this is easier to see with C++0x, which introduces even more
character-oriented types, types like char and wchar_t.

Should one have one extra stream for each of those types, perhaps?

I haven't checked, but if the committee has done that then they've gone off
their collective rockers.


> And while the standard says that wchar_t
> can be a char (in which case, wide character streams are rather
> useless), that's not the case on any of the machines I have
> ready access to.

That's not the point.

Bo Persson

unread,
Jun 29, 2009, 3:38:42 PM6/29/09
to
Alf P. Steinbach wrote:
> * Bo Persson:
>> Donkey Hottie wrote:
>>> "Bo Persson" <b...@gmb.dk> wrote in message
>>> news:7aonmaF...@mid.individual.net
>>>> On recent versions of Windows, the question is "Why do we
>>>> need cout, when wcout works for both narrow and wide
>>>> strings?".
>>>> On other systems, the question might be different.
>>>>
>>> So why the Windows implementation defines a new wcout, and not
>>> re-define cout in the first place?
>>
>> It is not new, they are both in the language standard. It is just
>> that as newer Windows versions internally uses wchar_t for
>> characters, wcout is a better match.
>
> I'm not sure I understand what you're talking about.
>
> Could you sort of elaborate?

I'm not sure I understand what you don't understand.

Is it the design to use a 16-bit character set in the OS, but keep
char and cout 8-bit wide? Or is it my preference of using wcout for
the occational console output, taking advantage of a 1-to-1 mappning
to the resulting byte stream?


Bo Persson


Alf P. Steinbach

unread,
Jun 29, 2009, 3:48:06 PM6/29/09
to
* Bo Persson:

> Alf P. Steinbach wrote:
>> * Bo Persson:
>>> Donkey Hottie wrote:
>>>> "Bo Persson" <b...@gmb.dk> wrote in message
>>>> news:7aonmaF...@mid.individual.net
>>>>> On recent versions of Windows, the question is "Why do we
>>>>> need cout, when wcout works for both narrow and wide
>>>>> strings?".
>>>>> On other systems, the question might be different.
>>>>>
>>>> So why the Windows implementation defines a new wcout, and not
>>>> re-define cout in the first place?
>>> It is not new, they are both in the language standard. It is just
>>> that as newer Windows versions internally uses wchar_t for
>>> characters, wcout is a better match.
>> I'm not sure I understand what you're talking about.
>>
>> Could you sort of elaborate?
>
> I'm not sure I understand what you don't understand.
>
> Is it the design to use a 16-bit character set in the OS, but keep
> char and cout 8-bit wide?

No, I understand that well.

It was done in a stupid way that made console windows effectively incompatible
with the rest of Windows, for the ordinary end user.


> Or is it my preference of using wcout for
> the occational console output, taking advantage of a 1-to-1 mappning
> to the resulting byte stream?

There is no 1-to-1 mapping.

It is mapping that *loses* information.

Even if you use some non-standard UTF-8 "locale" you're screwed, because in
Windows XP the UTF-8 codepage, 65001, does not work. "Does not work" means, for
example, that ordinary commands stop having any effect when you switch to this
codepage (and e.g. the 'more' command will, silly enough, report that it's out
of memory). So it "can't" be used for output until Windows XP is well dead.


Cheers & hth.,

- Alf

--

James Kanze

unread,
Jun 30, 2009, 3:55:34 AM6/30/09
to
On Jun 29, 11:22 am, "Alf P. Steinbach" <al...@start.no> wrote:
> * James Kanze:
> > On Jun 28, 10:58 pm, "Alf P. Steinbach" <al...@start.no> wrote:
> >> * James Kanze:
> >>> On Jun 27, 10:17 pm, "Alf P. Steinbach" <al...@start.no> wrote:
> >>>> * Amit Kumar:

> >>>>> then why do we need wcout?

> >>>> We don't, not in the form it has (translating to narrow
> >>>> characters). It's an abomination, a monstrosity, a completely
> >>>> redundant appendix in the acidic digestive system of C++, the
> >>>> system which end-product is... well, u know. ;-)

> >>> I'm not sure what your point is.

> >> Mostly that wcout is an abomination, a monstrosity, so on.

> > I know. You don't like iostream. For at least certain aspects
> > of the wide character streams, I agree with you. But that's
> > neither here nor there. We need something to do the job.

> Yes, and it seems the error of the committee on this one was
> to take something rather silly, look at it, "hey, this is
> something", and concluding, from the earlier established need
> for something, that therefore the silly was needed.

The issue was a bit more complicated than that. And the basic
idea (having separate wide character streams) isn't
fundamentally that bad.

> >> Given that anyone would want to use std::cout, then that's
> >> where conversion from various types to sequences of bytes is
> >> handled. There's no reason to have a separate stream for just
> >> one special small set of types; it's so stupid that it isn't
> >> even wrong.

> > I fail to understand what you're saying. The wide character
> > streams don't deal in sequences of bytes at all; they deal in
> > sequences of wchar_t.

> Nope, the appearance that they deal in wchar_t sequences is
> just appearance, cosmetics, complication. It may have been the
> original intention, who knows. But what they /do/ is to
> convert to byte (char) sequences, the same as the narrow
> streams, and with the same destinations.

I don't know where you get that. The only conversion is in the
filebuf (so it doesn't affect a lot of wostream, which micht be
wostringstream, for example). And while stuffing it directly
into filebuf (rather than just having a filebuf for char, and
using an intermittent forwarding streambuf for the conversion)
is definitely a poor design decision, you still have to face the
fact that outside of your program, the world works in octets.
And that in most cases, the external encoding is not something
based on whatever the system uses for wchar_t (and may vary from
one file to the next).

But that's really a low level detail. You set your locale, and
forget about it. (It would have been better if the encoding had
been somehow separated from locale. It's rather a drag that if
I set the stream locale to fr_FR, I might also unwittingly
change the encoding.) All of the conversion functions, for
example, deal with wchar_t (in whatever encoding that is).

> So why should one have to deal with 2 streams converting two
> slightly different sets of types to char sequences on standard
> output, instead of just 1 stream converting any of those types
> to char sequences on standard output?

Because that's life. Different files use different encodings,
and internally, if you're using UTF-32 or UTF-16, you'll handle
things differently than if you're using UTF-8, or even ISO
8859-1. Ideally, there would be only one encoding, it would be
"single byte" (UTF-32), and everything would work with it.
Practically, there are hundreds of different encodings, and
there are a lot of programs or programmers who don't want the
overhead of UTF-32 for their characters internally. (I tend to
use UTF-8 internally, for example. But the type of work I do
with text never involves arbitrary positionning in the text: I'm
either advancing, or returning to a previously saved position.
So the multi-byte issues aren't a problem.)

> There is no answer to that, for the design is just
> meaningless.

> And this is easier to see with C++0x, which introduces even
> more character-oriented types, types like char and wchar_t.

That's because of the lack of guarantees with regards to the
encoding of wchar_t. We have to deal with history---if we were
designing something from scratch, of course, there would be just
two character types, one with UTF-8, and one with UTF-32.

> Should one have one extra stream for each of those types,
> perhaps?

We probably should:-). As it stands, there's no practical way
to output text in char16_t and char32_t, which sort of limits
their usefulness.

> I haven't checked, but if the committee has done that then
> they've gone off their collective rockers.

What's the point in having character types which you can't use?

Alf P. Steinbach

unread,
Jun 30, 2009, 4:59:26 AM6/30/09
to
* James Kanze:
> On Jun 29, 11:22 am, "Alf P. Steinbach" <al...@start.no> wrote:
>> * James Kanze:
>>> On Jun 28, 10:58 pm, "Alf P. Steinbach" <al...@start.no> wrote:
>>>> * James Kanze:
>>>>> On Jun 27, 10:17 pm, "Alf P. Steinbach" <al...@start.no> wrote:
>>>>>> * Amit Kumar:
>
>>>>>>> then why do we need wcout?
>
>>>>>> We don't, not in the form it has (translating to narrow
>>>>>> characters). It's an abomination, a monstrosity, a completely
>>>>>> redundant appendix in the acidic digestive system of C++, the
>>>>>> system which end-product is... well, u know. ;-)
>
>>>>> I'm not sure what your point is.
>
>>>> Mostly that wcout is an abomination, a monstrosity, so on.
>
>>> I know. You don't like iostream. For at least certain aspects
>>> of the wide character streams, I agree with you. But that's
>>> neither here nor there. We need something to do the job.

Could you please stop adding stuff between quotes so as to take them out of
context? I didn't just just call names on wcout (even though those names *are*
appropriate). I gave simple clear reasons why it is a useless monstrosity.


>> Yes, and it seems the error of the committee on this one was
>> to take something rather silly, look at it, "hey, this is
>> something", and concluding, from the earlier established need
>> for something, that therefore the silly was needed.
>
> The issue was a bit more complicated than that. And the basic
> idea (having separate wide character streams) isn't
> fundamentally that bad.

I'm sorry, that's not meaningful to me.

As a generalization the latter sentence might be meaningful in some other
context, where we're not talking about std::wcout.


>>>> Given that anyone would want to use std::cout, then that's
>>>> where conversion from various types to sequences of bytes is
>>>> handled. There's no reason to have a separate stream for just
>>>> one special small set of types; it's so stupid that it isn't
>>>> even wrong.
>
>>> I fail to understand what you're saying. The wide character
>>> streams don't deal in sequences of bytes at all; they deal in
>>> sequences of wchar_t.
>
>> Nope, the appearance that they deal in wchar_t sequences is
>> just appearance, cosmetics, complication. It may have been the
>> original intention, who knows. But what they /do/ is to
>> convert to byte (char) sequences, the same as the narrow
>> streams, and with the same destinations.
>
> I don't know where you get that.

Have you tried actually using std::wcout, or std::wcerr?

std::wcout translates each wide character to a single narrow character, unless
you add in non-standard conversion.

It's a narrow character stream.


> The only conversion is in the
> filebuf (so it doesn't affect a lot of wostream, which micht be
> wostringstream, for example). And while stuffing it directly
> into filebuf (rather than just having a filebuf for char, and
> using an intermittent forwarding streambuf for the conversion)
> is definitely a poor design decision, you still have to face the
> fact that outside of your program, the world works in octets.
> And that in most cases, the external encoding is not something
> based on whatever the system uses for wchar_t (and may vary from
> one file to the next).

That's not directly technically incorrect, as far as I can see, but still, it's
just misleading techno-babble, i.e. a load of bull.


> But that's really a low level detail.

It doesn't matter what the beast produces?

That *is* what matters.

If std::wcout had produced wide encoding points it could have been useful, but
as it is, it's utterly and completely useless for anything serious (unless you
add in non-standard functionality).


> You set your locale, and
> forget about it. (It would have been better if the encoding had
> been somehow separated from locale. It's rather a drag that if
> I set the stream locale to fr_FR, I might also unwittingly
> change the encoding.) All of the conversion functions, for
> example, deal with wchar_t (in whatever encoding that is).
>
>> So why should one have to deal with 2 streams converting two
>> slightly different sets of types to char sequences on standard
>> output, instead of just 1 stream converting any of those types
>> to char sequences on standard output?
>
> Because that's life.

When that's the best defense you can come up with, doesn't it tell you something
about the design?


[snip]


> What's the point in having character types which you can't use?

It's absurd to think that a more sensible design would not provide a way to do
wide character i/o.

0 new messages