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

Re: novice: small annoyance

0 views
Skip to first unread message

Mike Wahler

unread,
Dec 16, 2004, 4:26:29 PM12/16/04
to
"Christo" <ch...@juststuffd.co.uk> wrote in message
news:32ec5kF...@individual.net...
> i am displaying float values
>
> 8.5
>
> 10.8 etc
>
> how can i make them appear as
>
> 8.50
>
> 10.80
>
> they are prices to be honest and £8.5 isnt propper, where as £8.50 is

First, don't use floating point types for currency.
They're inherently inaccurate ('rounding errors' can
accumulate and cause incorrect results). Use an integral
type (e.g. 'long') to represent the smallest unit
(e.g. pence) and have your output logic place the decimal
point.

Also, when you do want to use floating-point types,
prefer 'double' over 'float'. You'll get a much
larger range, and better accuracy.

Anyway, to answer your question about formatting a float
(or double):


C:
double d(8.5);
printf("%.2f", d); /* <stdio.h> */


C++:

Same as for C, or:

double d(8.5);

std::cout /* <iostream> */
<< std::fixed /* <ios> */
<< std::setprecision(2) /* <iomanip> */
<< d;


Which (C and/or C++) book(s) are you reading which
do not explain this?

-Mike


David White

unread,
Dec 16, 2004, 4:59:14 PM12/16/04
to
"Christo" <ch...@juststuffd.co.uk> wrote in message
news:32ec5kF...@individual.net...
> i am displaying float values
>
> 8.5
>
> 10.8 etc
>
> how can i make them appear as
>
> 8.50
>
> 10.80
>
> they are prices to be honest and £8.5 isnt propper, where as £8.50 is
>
> thanks (in advance)
>
> chris

(For C++ only)
You need to set the fixed flag and the precision to 2.
Example:

#include <iostream>

void outAmount(double amount)
{
std::cout.setf(std::ios_base::fixed, std::ios_base::floatfield);
std::cout.precision(2);
std::cout << amount << std::endl;
}

Or, perhaps this example looks a little less cluttered:

#include <iostream>

using namespace std;

void outAmount(double amount)
{
cout.setf(ios_base::fixed, ios_base::floatfield);
cout.precision(2);
cout << amount << endl;
}

You can also do it with manipulators:

#include <iostream>
#include <iomanip>

void outAmount(double amount)
{
std::cout << std::fixed << std::setprecision(2) << amount << std::endl;
}

DW


Mike Wahler

unread,
Dec 16, 2004, 6:11:54 PM12/16/04
to

"David White" <n...@email.provided> wrote in message
news:KBnwd.666$i6....@nasal.pacific.net.au...

> "Christo" <ch...@juststuffd.co.uk> wrote in message
> news:32ec5kF...@individual.net...
> > i am displaying float values
> >
> > 8.5
> >
> > 10.8 etc
> >
> > how can i make them appear as
> >
> > 8.50
> >
> > 10.80
> >
> > they are prices to be honest and £8.5 isnt propper, where as £8.50 is
> >
> > thanks (in advance)
> >
> > chris
>
> (For C++ only)
> You need to set the fixed flag and the precision to 2.
> Example:
>
> #include <iostream>

#include <ios> /* for 'std::ios_base' */
#include <ostream> /* for 'std::endl' */

> void outAmount(double amount)
> {
> std::cout.setf(std::ios_base::fixed, std::ios_base::floatfield);
> std::cout.precision(2);
> std::cout << amount << std::endl;
> }
>
> Or, perhaps this example looks a little less cluttered:
>
> #include <iostream>

#include <ios> /* for 'std::ios_base' */
#include <ostream> /* for 'std::endl' */

>
> using namespace std;
>
> void outAmount(double amount)
> {
> cout.setf(ios_base::fixed, ios_base::floatfield);
> cout.precision(2);
> cout << amount << endl;
> }
>
> You can also do it with manipulators:
>
> #include <iostream>
> #include <iomanip>

#include <ios> /* for 'std::fixed' */
#include <ostream> /* for 'std::endl' */

>
> void outAmount(double amount)
> {
> std::cout << std::fixed << std::setprecision(2) << amount << std::endl;
> }
>
> DW

-Mike


David White

unread,
Dec 16, 2004, 6:25:26 PM12/16/04
to
"Mike Wahler" <mkwa...@mkwahler.net> wrote in message
news:_Cowd.1421$9j5....@newsread3.news.pas.earthlink.net...

>
> "David White" <n...@email.provided> wrote in message
> news:KBnwd.666$i6....@nasal.pacific.net.au...
> > #include <iostream>
>
> #include <ios> /* for 'std::ios_base' */
> #include <ostream> /* for 'std::endl' */

So, you are claiming that it is conceivable to #include <iostream> without
implicitly #including <ios> and <ostream>?

DW


Mike Wahler

unread,
Dec 16, 2004, 6:52:58 PM12/16/04
to
"David White" <n...@email.provided> wrote in message
news:xSowd.669$i6....@nasal.pacific.net.au...

Yes, of course it is (though yes, I know many/most implementations
would do that implicit #inclusion). But if your code does not #include
a particular standard header, you have no guarantee that the names declared
by that header will be visible.

The standard specifically allows standard headers to #include
one another, but there is absolutely no requirement that any
of them do.

-Mike


Alwyn

unread,
Dec 16, 2004, 6:52:44 PM12/16/04
to
On Fri, 17 Dec 2004 10:25:26 +1100, David White wrote:

> "Mike Wahler" <mkwa...@mkwahler.net> wrote in message
> news:_Cowd.1421$9j5....@newsread3.news.pas.earthlink.net...
>>

>> #include <ios> /* for 'std::ios_base' */
>> #include <ostream> /* for 'std::endl' */
>
> So, you are claiming that it is conceivable to #include <iostream> without
> implicitly #including <ios> and <ostream>?

Forget it! 'iostream; and 'iomanip' are the only headers required here.


Alwyn

Mike Wahler

unread,
Dec 16, 2004, 7:08:40 PM12/16/04
to

"Alwyn" <al...@blueyonder.co.uk> wrote in message
news:pan.2004.12.16....@blueyonder.co.uk...

Not true. Neither of those headers are required to declare
'std::endl' or 'std::ios_base' (I'm actually not sure if they're
prohibited from doing so, though). (Often an implementation's
<iostream> will #include <ios> and <ostream>, but there's
no requirement that they do.

-Mike


David White

unread,
Dec 16, 2004, 7:09:36 PM12/16/04
to
"Mike Wahler" <mkwa...@mkwahler.net> wrote in message
news:udpwd.1455$9j5....@newsread3.news.pas.earthlink.net...

> "David White" <n...@email.provided> wrote in message
> news:xSowd.669$i6....@nasal.pacific.net.au...
> > So, you are claiming that it is conceivable to #include <iostream>
without
> > implicitly #including <ios> and <ostream>?
>
> Yes, of course it is (though yes, I know many/most implementations
> would do that implicit #inclusion). But if your code does not #include
> a particular standard header, you have no guarantee that the names
declared
> by that header will be visible.
>
> The standard specifically allows standard headers to #include
> one another, but there is absolutely no requirement that any
> of them do.

Well, that's preposterous. No sane implementor is going to repeat the class
definition of std::ostream in <iostream> when <ostream> can be simply be
#included. Not to mention all the code that would break. You might well be
the only programmer on the planet who includes those headers explictly.

DW


Christo

unread,
Dec 16, 2004, 7:19:54 PM12/16/04
to

"Mike Wahler" <mkwa...@mkwahler.net> wrote in message
news:94nwd.1291$9j5....@newsread3.news.pas.earthlink.net...

thanks for the help

i am currently reading "essence of c++" i havent been readin it really, just
experimenting things, it is just a simple weight calculator for orders i am
working on and it has to output the cost, etc etc, i will probably come to a
section on this later in the learning process (software development at uni)
pretty much basic io stuff we are doing now, few loops and if statements and
just starting to do arrays.

it probably isnt required but i dont like it to be imperfect, it isnt the
way i am you know 8 point 5 pounds doesnt sound at all right when it should
be 8 pounds 50

thanks though

Chris


Alwyn

unread,
Dec 16, 2004, 7:28:55 PM12/16/04
to

The 'iostream' header gives you both 'ostream' and 'istream'. As the
Dumkumware site says: 'This is often the only header you need include to
perform input and output from a C++ program.' Further, 'basic_ostream' and
'basic_istream' inherit from 'basic_ios', which inherits from 'ios_base',
so 'ios' will always be included. Again from the Dinkumware site: 'Include
the iostreams standard header <ios> to define several types and functions
basic to the operation of iostreams. (This header is typically included
for you by another of the iostreams headers. You seldom have occasion to
include it directly.)'

In the examples in his book on the standard library, Josuttis only
includes 'ostream' where 'iostream' is not required; I cannot find a
single example in which he includes 'ios'. The pattern is similar in the
examples from the Kreft and langer book on IOStreams too. What's good
enough for them should certainly be good enough for anybody here.


Alwyn

Mike Wahler

unread,
Dec 16, 2004, 7:35:34 PM12/16/04
to
"David White" <n...@email.provided> wrote in message
news:Yvpwd.671$i6....@nasal.pacific.net.au...

> "Mike Wahler" <mkwa...@mkwahler.net> wrote in message
> news:udpwd.1455$9j5....@newsread3.news.pas.earthlink.net...
> > "David White" <n...@email.provided> wrote in message
> > news:xSowd.669$i6....@nasal.pacific.net.au...
> > > So, you are claiming that it is conceivable to #include <iostream>
> without
> > > implicitly #including <ios> and <ostream>?
> >
> > Yes, of course it is (though yes, I know many/most implementations
> > would do that implicit #inclusion). But if your code does not #include
> > a particular standard header, you have no guarantee that the names
> declared
> > by that header will be visible.
> >
> > The standard specifically allows standard headers to #include
> > one another, but there is absolutely no requirement that any
> > of them do.
>
> Well, that's preposterous.

If you feel that way, then take it up with ISO.

> No sane implementor is going to repeat the class
> definition of std::ostream in <iostream> when <ostream> can be simply be
> #included.

The implementor can do it however he likes, whether you consider
it 'sane' or not, as long as the required names are visible.
E.g. <iostream> is not required to declare e.g. 'std::ostream',
directly or indirectly. Anyway, my #inclusion of <ostream>
in the code was not for 'std::ostream', but for 'std::endl'.

You seem to be advocating dependence upon a non-required
implementation strategy. I don't do that. Of course
you're free to do so if you like. But were you to write
such code for me, I would reject it.

> Not to mention all the code that would break.

That would *not* be the fault of the language or library,
but of the code. Such code itself is already 'broken',
it's simply taking advantage of an (admittedly common)
implementation method. Depending upon nonrequired
implementation methods is imo not a good idea.

>You might well be
> the only programmer on the planet who includes those headers explictly.

Of course I won't let my code depend upon implicit
behavior (however ubiquitous) which is not required.
If I'm alone in this, so be it.

When I write code, I strive for correctness and maximum
portability (including to implementations not yet created),
not company or consensus.

Anyway, take a look in e.g. Josuttis or L & K. I'm *not* alone.
But that doesn't really matter imo.

-Mike


Mike Wahler

unread,
Dec 16, 2004, 7:45:36 PM12/16/04
to
"Christo" <ch...@juststuffd.co.uk> wrote in message
news:32en18F...@individual.net...

>
> "Mike Wahler" <mkwa...@mkwahler.net> wrote in message
> news:94nwd.1291$9j5....@newsread3.news.pas.earthlink.net...
> > Which (C and/or C++) book(s) are you reading which
> > do not explain this?
> >
> > -Mike
> >
> >
>
> thanks for the help
>
> i am currently reading "essence of c++"

I'm not familiar with that one, so I cannot comment upon
its quality. May I ask the author and publication date?

I for one would be interested in opinions of any 'gurus'
who might be familiar with it (I checked ACCU, didn't
see a review there).

>i havent been readin it really,

Why not? Not much point in buying it then, is there? :-)

>just
> experimenting things,

Experimentation can be fun and even useful, but without
some grounding (i.e. from a quality text), it can easily
lead to confusion and incorrect 'knowledge'. Under the
right circumstances, such 'knowledge' can cause much
damage.

>it is just a simple weight calculator for orders i am
> working on and it has to output the cost, etc etc, i will probably come to
a
> section on this later in the learning process (software development at
uni)
> pretty much basic io stuff we are doing now, few loops and if statements
and
> just starting to do arrays.

Imo teaching arrays before containers in a C++ curriculum
is Not Good. I feel that the 'low level' stuff such as
arrays and pointers should be left for the 'advanced'
portion of the course. Others opinions may differ.

>
> it probably isnt required but i dont like it to be imperfect, it isnt the
> way i am you know 8 point 5 pounds doesnt sound at all right when it
should
> be 8 pounds 50

I already showed you how to do that.

-Mike


Mike Wahler

unread,
Dec 16, 2004, 7:52:12 PM12/16/04
to
"Alwyn" <al...@blueyonder.co.uk> wrote in message
news:pan.2004.12.17....@blueyonder.co.uk...

> On Fri, 17 Dec 2004 00:08:40 +0000, Mike Wahler wrote:
>
> >
> > "Alwyn" <al...@blueyonder.co.uk> wrote in message
> > news:pan.2004.12.16....@blueyonder.co.uk...
> >> On Fri, 17 Dec 2004 10:25:26 +1100, David White wrote:
> >>
> >> > "Mike Wahler" <mkwa...@mkwahler.net> wrote in message
> >> > news:_Cowd.1421$9j5....@newsread3.news.pas.earthlink.net...
> >> >>
> >> >> #include <ios> /* for 'std::ios_base' */
> >> >> #include <ostream> /* for 'std::endl' */
> >> >
> >> > So, you are claiming that it is conceivable to #include <iostream>
> > without
> >> > implicitly #including <ios> and <ostream>?
> >>
> >> Forget it! 'iostream; and 'iomanip' are the only headers required here.
> >
> > Not true. Neither of those headers are required to declare
> > 'std::endl' or 'std::ios_base' (I'm actually not sure if they're
> > prohibited from doing so, though). (Often an implementation's
> > <iostream> will #include <ios> and <ostream>, but there's
> > no requirement that they do.
>
> The 'iostream' header gives you both 'ostream' and 'istream'.

It might, it might not. It's not prohibited from doing so,
but the important point is that it is *not* required to do so.

> As the
> Dumkumware site says: 'This is often the only header you need include to
> perform input and output from a C++ program.'

I get my language rules from ISO 14882, not any
particular implementor.

>Further, 'basic_ostream' and
> 'basic_istream' inherit from 'basic_ios', which inherits from 'ios_base',
> so 'ios' will always be included.

Only a particular implementor can make that claim, about his
implementation. Such a claim about the standard language/library
is simply incorrect.

>Again from the Dinkumware site: 'Include
> the iostreams standard header <ios> to define several types and functions
> basic to the operation of iostreams. (This header is typically included
> for you by another of the iostreams headers. You seldom have occasion to
> include it directly.)'

Again, I write to ISO, not Dinkumware. (I do use their
library, but I don't depend upon its particular implementation
strategy, which again, is *NOT* required).

> In the examples in his book on the standard library, Josuttis only
> includes 'ostream' where 'iostream' is not required; I cannot find a
> single example in which he includes 'ios'. The pattern is similar in the
> examples from the Kreft and langer book on IOStreams too. What's good
> enough for them should certainly be good enough for anybody here.

I may have been mistaken. I don't have those books to hand right now,
but I'll look again when I do.

Anyway, I also don't take Josuttis or L&K as the ultimate
authority. I take ISO.

-Mike


David White

unread,
Dec 16, 2004, 8:05:47 PM12/16/04
to
"Mike Wahler" <mkwa...@mkwahler.net> wrote in message
news:qRpwd.1483$9j5....@newsread3.news.pas.earthlink.net...

> "David White" <n...@email.provided> wrote in message
> news:Yvpwd.671$i6....@nasal.pacific.net.au...
> > Well, that's preposterous.
>
> If you feel that way, then take it up with ISO.

It should be taken up with ISO. If what you say is true, and I don't doubt
that it is, the standard should have anticipated that people naturally
include headers only until their code compiles. Therefore, to ensure that
code complies with the standard, they should have insisted that implementors
ensure that every reference to a definition in std:: be undefined unless the
specific header containing that definition is explicitly #included. By not
doing this, the standard effectively guarantees that most code won't comply
with the standard. It's all very well to say that it's not the standard's
fault, but any standard that doesn't allow for normal behaviour isn't very
useful as a standard.

> > No sane implementor is going to repeat the class
> > definition of std::ostream in <iostream> when <ostream> can be simply be
> > #included.
>
> The implementor can do it however he likes, whether you consider
> it 'sane' or not, as long as the required names are visible.
> E.g. <iostream> is not required to declare e.g. 'std::ostream',
> directly or indirectly.

That seems a little odd. Isn't std::cout defined in <iostream>, and isn't
std::cout an instance of std::ostream? I wonder what header gymnastics are
required to enable std::cout to be used without std::ostream being declared.

> Anyway, my #inclusion of <ostream>
> in the code was not for 'std::ostream', but for 'std::endl'.
>
> You seem to be advocating dependence upon a non-required
> implementation strategy. I don't do that. Of course
> you're free to do so if you like. But were you to write
> such code for me, I would reject it.
>
> > Not to mention all the code that would break.
>
> That would *not* be the fault of the language or library,
> but of the code.

But the language could safely be charged with being complicit in the crime.

> Such code itself is already 'broken',
> it's simply taking advantage of an (admittedly common)
> implementation method. Depending upon nonrequired
> implementation methods is imo not a good idea.
>
> >You might well be
> > the only programmer on the planet who includes those headers explictly.
>
> Of course I won't let my code depend upon implicit
> behavior (however ubiquitous) which is not required.
> If I'm alone in this, so be it.
>
> When I write code, I strive for correctness and maximum
> portability (including to implementations not yet created),
> not company or consensus.

I'm sure you're right about the standard, and therefore you are also right
to point it out. However, those who prepared the standard were quite
unrealistic in their expectations.

DW


Alwyn

unread,
Dec 16, 2004, 8:07:23 PM12/16/04
to
On Fri, 17 Dec 2004 00:52:12 +0000, Mike Wahler wrote:
>
> Anyway, I also don't take Josuttis or L&K as the ultimate
> authority. I take ISO.

OK, guess where this little example comes from:

#include <iostream>

int main()
{
using namespace std;
const int line_buffer_size = 100;

char buffer[line_buffer_size];
int line_number = 0;
while (cin.getline(buffer, line_buffer_size, '\n') || cin.gcount()) {
int count = cin.gcount();
if (cin.eof())
cout << "Partial final line"; // cin.fail() is false
else if (cin.fail()) {
cout << "Partial long line";
cin.clear(cin.rdstate() & ~ios::failbit);
} else {
count--; // Don't include '\n' in count
cout << "Line " << ++line_number;
}
cout << " (" << count << " chars): " << buffer << endl;
}
}

<http://www.open-std.org/jtc1/sc22/open/n2356/>
:-)


Alwyn

Mike Wahler

unread,
Dec 16, 2004, 8:24:24 PM12/16/04
to

"Alwyn" <al...@blueyonder.co.uk> wrote in message
news:pan.2004.12.17...@blueyonder.co.uk...

> On Fri, 17 Dec 2004 00:52:12 +0000, Mike Wahler wrote:
> >
> > Anyway, I also don't take Josuttis or L&K as the ultimate
> > authority. I take ISO.
>
> OK, guess where this little example comes from:

Doesn't matter. It's not 100% conformant, regardless
the source. When I said I get my 'usage rules' from
ISO, I meant the ISO 14882 document, not anything
I see that might have "ISO" attached to it.

-Mike

Alwyn

unread,
Dec 16, 2004, 8:24:49 PM12/16/04
to
On Fri, 17 Dec 2004 00:52:12 +0000, Mike Wahler wrote:

> "Alwyn" <al...@blueyonder.co.uk> wrote in message
> news:pan.2004.12.17....@blueyonder.co.uk...
>> On Fri, 17 Dec 2004 00:08:40 +0000, Mike Wahler wrote:
>
>> Further, 'basic_ostream' and
>> 'basic_istream' inherit from 'basic_ios', which inherits from 'ios_base',
>> so 'ios' will always be included.
>
> Only a particular implementor can make that claim, about his
> implementation. Such a claim about the standard language/library
> is simply incorrect.

I suggest you read the standard again for the inheritance hierarchy. If a
header contains a class definition and the class being defined inherits
from another class, it will have to include the header that defines the
other class.


Alwyn

Old Wolf

unread,
Dec 16, 2004, 8:27:20 PM12/16/04
to
David White wrote:

> "Mike Wahler" <mkwa...@mkwahler.net> wrote:
> > The standard specifically allows standard headers to #include
> > one another, but there is absolutely no requirement that any
> > of them do.
>
> Well, that's preposterous. No sane implementor is going to repeat
> the class definition of std::ostream in <iostream> when <ostream>
> can be simply be #included.

It's common for <iosfwd> to contain all those things, and then
<ostream> only need to include <iosfwd> and then define endl and ends,
and <iostream> includes <iosfwd> and defines cin, cout, cerr etc.

> Not to mention all the code that would break. You might well be
> the only programmer on the planet who includes those headers
> explictly.

There was a case in c.l.c++ recently where someone went:

#include <iostream>
int main()
{
std::cout << "Hello, world!\n";
}

and got a pointer value displayed. The reason is that the
basic_ostream member function operator<<(void const *) was
invoked. Since the poster hadn't included <ostream>,
the free function operator<<(basic_ostream<T> &, char const *)
was not in scope.

Alwyn

unread,
Dec 16, 2004, 8:28:08 PM12/16/04
to
On Fri, 17 Dec 2004 01:24:24 +0000, Mike Wahler wrote:

>
> "Alwyn" <al...@blueyonder.co.uk> wrote in message
> news:pan.2004.12.17...@blueyonder.co.uk...
>> On Fri, 17 Dec 2004 00:52:12 +0000, Mike Wahler wrote:
>> >
>> > Anyway, I also don't take Josuttis or L&K as the ultimate
>> > authority. I take ISO.
>>
>> OK, guess where this little example comes from:
>
> Doesn't matter. It's not 100% conformant, regardless
> the source. When I said I get my 'usage rules' from
> ISO, I meant the ISO 14882 document, not anything
> I see that might have "ISO" attached to it.

That was from the 1997 Public Review document. Are you telling us that
that example does not occur in the ISO document? Or maybe they changed it
to conform to your rules?


Alwyn

Old Wolf

unread,
Dec 16, 2004, 8:30:21 PM12/16/04
to
David White wrote:
> "Mike Wahler" <mkwa...@mkwahler.net> wrote:
> > The standard specifically allows standard headers to #include
> > one another, but there is absolutely no requirement that any
> > of them do.
>
> Well, that's preposterous. No sane implementor is going to repeat
> the class definition of std::ostream in <iostream> when <ostream>
> can be simply be #included.

It's common for <iosfwd> to contain all those things, and then


<ostream> only need to include <iosfwd> and then define endl and ends,
and <iostream> includes <iosfwd> and defines cin, cout, cerr etc.

> Not to mention all the code that would break. You might well be


> the only programmer on the planet who includes those headers
> explictly.

There was a case in c.l.c++ recently where someone went:

David White

unread,
Dec 16, 2004, 8:51:01 PM12/16/04
to
"Old Wolf" <old...@inspire.net.nz> wrote in message
news:1103246840.6...@z14g2000cwz.googlegroups.com...

> David White wrote:
> There was a case in c.l.c++ recently where someone went:
>
> #include <iostream>
> int main()
> {
> std::cout << "Hello, world!\n";
> }
>
> and got a pointer value displayed. The reason is that the
> basic_ostream member function operator<<(void const *) was
> invoked. Since the poster hadn't included <ostream>,
> the free function operator<<(basic_ostream<T> &, char const *)
> was not in scope.

And how did <iostream> manage to include the class definition of
std::ostream without including <ostream>?

DW


Mike Wahler

unread,
Dec 16, 2004, 8:56:11 PM12/16/04
to

"Old Wolf" <old...@inspire.net.nz> wrote in message
news:1103247021.5...@z14g2000cwz.googlegroups.com...

> David White wrote:
> > "Mike Wahler" <mkwa...@mkwahler.net> wrote:
> > > The standard specifically allows standard headers to #include
> > > one another, but there is absolutely no requirement that any
> > > of them do.
> >
> > Well, that's preposterous. No sane implementor is going to repeat
> > the class definition of std::ostream in <iostream> when <ostream>
> > can be simply be #included.
>
> It's common for <iosfwd> to contain all those things, and then
> <ostream> only need to include <iosfwd> and then define endl and ends,
> and <iostream> includes <iosfwd> and defines cin, cout, cerr etc.
>
> > Not to mention all the code that would break. You might well be
> > the only programmer on the planet who includes those headers
> > explictly.
>
> There was a case in c.l.c++ recently where someone went:
>
> #include <iostream>
> int main()
> {
> std::cout << "Hello, world!\n";
> }
>
> and got a pointer value displayed.

Then I don't think the implementation is conforming.
Do you recall which one it was?


> The reason is that the
> basic_ostream member function operator<<(void const *) was
> invoked. Since the poster hadn't included <ostream>,

I don't think that's required for the program to
output the characters of the string literal.

-Mike

Mike Wahler

unread,
Dec 16, 2004, 8:59:00 PM12/16/04
to
"Alwyn" <al...@blueyonder.co.uk> wrote in message
news:pan.2004.12.17....@blueyonder.co.uk...

No I'm not.

> Or maybe they changed it

Doesn't matter. It's a *example*, it does not comprise
a requirement, constraint, etc. Also it's well known
that the standard document isn't perfect. But I certainly
won't let my code depend upon behavior not explicitly
mandated by the standard.

> to conform to your rules?

They're not *my* rules.

-Mike


Mike Wahler

unread,
Dec 16, 2004, 9:34:25 PM12/16/04
to

"Alwyn" <al...@blueyonder.co.uk> wrote in message
news:pan.2004.12.17....@blueyonder.co.uk...
> On Fri, 17 Dec 2004 00:52:12 +0000, Mike Wahler wrote:
>
> > "Alwyn" <al...@blueyonder.co.uk> wrote in message
> > news:pan.2004.12.17....@blueyonder.co.uk...
> >> On Fri, 17 Dec 2004 00:08:40 +0000, Mike Wahler wrote:
> >
> >> Further, 'basic_ostream' and
> >> 'basic_istream' inherit from 'basic_ios', which inherits from
'ios_base',
> >> so 'ios' will always be included.
> >
> > Only a particular implementor can make that claim, about his
> > implementation. Such a claim about the standard language/library
> > is simply incorrect.
>
> I suggest you read the standard again for the inheritance hierarchy.

The form of the heirarchy does not impose any requirement
that any standard header #include any other, or make any
names visible which are not specified for a given header.

E.g.

#include <iostream>

/*
Required to be visible:
'std::cin'
'std::cout'
'std::cerr'
'std::clog'
'std::wcin'
'std::wcout'
'std::wcerr'
'std::wclog'

No other names required to be visible
*/

int main()
{
std::cout << "hey!\n"; /* must be translated */
std::ostream o; /* not required to be translated */
/* (diagnostic allowed, not sure if */
/* required) */

return 0;
}


>If a
> header contains a class definition and the class being defined inherits
> from another class, it will have to include the header that defines the
> other class.

It can, and often does (because that's typically the easiest
way to do it). But there's no requirement that it does.
And even if it does, the names from any standard headers
#included by others are not required to be visible to the
program.

And there's no requirement that any needed names be
supplied (to the #included header) by another header at all).

If you feel differently, please cite the relevant portion(s) of
14882.

-Mike

James Dennett

unread,
Dec 16, 2004, 11:48:07 PM12/16/04
to
David White wrote:

Absolutely. <iostream> is only required to declare a
number of objects. It might include no other headers.
Indeed a good implementation might well avoid including
all of <ios> and <ostream>.

Pedantically,

#include <iostream>
int main() {
std::cout << "Hello world\n";
}

is not portable as the correct operator<< is not required
to be declared by #include <iostream>, so #include <ostream>
ought to be added. However, very few compilers/library
implementations would cause this traditional example code
to fail to compile.

-- James

James Dennett

unread,
Dec 16, 2004, 11:50:46 PM12/16/04
to
Mike Wahler wrote:

> "Alwyn" <al...@blueyonder.co.uk> wrote in message
> news:pan.2004.12.16....@blueyonder.co.uk...
>
>>On Fri, 17 Dec 2004 10:25:26 +1100, David White wrote:
>>
>>
>>>"Mike Wahler" <mkwa...@mkwahler.net> wrote in message
>>>news:_Cowd.1421$9j5....@newsread3.news.pas.earthlink.net...
>>>
>>>>#include <ios> /* for 'std::ios_base' */
>>>>#include <ostream> /* for 'std::endl' */
>>>
>>>So, you are claiming that it is conceivable to #include <iostream>
>
> without
>
>>>implicitly #including <ios> and <ostream>?
>>
>>Forget it! 'iostream; and 'iomanip' are the only headers required here.
>
>
> Not true. Neither of those headers are required to declare
> 'std::endl' or 'std::ios_base' (I'm actually not sure if they're
> prohibited from doing so, though).

There's no prohibition; while C define strictly what each
header can declare/define, C++ does not do so, and allows
any standard header to include any other as one situation.
A legal, though suboptimal, implementation would make all
of the "normal" headers do a #include <all>, where <all>
is a header which includes appropriate declarations and
definition for the whole standard library (excluding the
C-compatibility headers and <cassert>).

> (Often an implementation's
> <iostream> will #include <ios> and <ostream>, but there's
> no requirement that they do.

True.

James Dennett

unread,
Dec 16, 2004, 11:58:51 PM12/16/04
to
David White wrote:

> "Mike Wahler" <mkwa...@mkwahler.net> wrote in message
> news:udpwd.1455$9j5....@newsread3.news.pas.earthlink.net...
>
>>"David White" <n...@email.provided> wrote in message
>>news:xSowd.669$i6....@nasal.pacific.net.au...
>>
>>>So, you are claiming that it is conceivable to #include <iostream>
>
> without
>
>>>implicitly #including <ios> and <ostream>?
>>
>>Yes, of course it is (though yes, I know many/most implementations
>>would do that implicit #inclusion). But if your code does not #include
>>a particular standard header, you have no guarantee that the names
>
> declared
>
>>by that header will be visible.
>>
>>The standard specifically allows standard headers to #include
>>one another, but there is absolutely no requirement that any
>>of them do.
>
>
> Well, that's preposterous. No sane implementor is going to repeat the class
> definition of std::ostream in <iostream> when <ostream> can be simply be
> #included.

It's not necessary to do so in order to declare the standard
stream objects.

> Not to mention all the code that would break. You might well be
> the only programmer on the planet who includes those headers explictly.

No. He's not alone. But you do have a point; strict implementations
have existed, and have mostly been changed to allow sloppier coding.

-- James

James Dennett

unread,
Dec 17, 2004, 12:02:18 AM12/17/04
to
David White wrote:

> "Mike Wahler" <mkwa...@mkwahler.net> wrote in message
> news:qRpwd.1483$9j5....@newsread3.news.pas.earthlink.net...
>
>>"David White" <n...@email.provided> wrote in message
>>news:Yvpwd.671$i6....@nasal.pacific.net.au...
>>
>>>Well, that's preposterous.
>>
>>If you feel that way, then take it up with ISO.
>
>
> It should be taken up with ISO. If what you say is true, and I don't doubt
> that it is, the standard should have anticipated that people naturally
> include headers only until their code compiles. Therefore, to ensure that
> code complies with the standard, they should have insisted that implementors
> ensure that every reference to a definition in std:: be undefined unless the
> specific header containing that definition is explicitly #included. By not
> doing this, the standard effectively guarantees that most code won't comply
> with the standard. It's all very well to say that it's not the standard's
> fault, but any standard that doesn't allow for normal behaviour isn't very
> useful as a standard.

It's a flaw in the standard, and one the committee knew about
at the time; a lot of work went towards trying to pin down the
allowable declarations for each header, but it could not be
completed in time to get the 1998 standard out.

>>>No sane implementor is going to repeat the class
>>>definition of std::ostream in <iostream> when <ostream> can be simply be
>>>#included.
>>
>>The implementor can do it however he likes, whether you consider
>>it 'sane' or not, as long as the required names are visible.
>>E.g. <iostream> is not required to declare e.g. 'std::ostream',
>>directly or indirectly.
>
>
> That seems a little odd. Isn't std::cout defined in <iostream>,

No, it's declared there but not defined.

> and isn't
> std::cout an instance of std::ostream? I wonder what header gymnastics are
> required to enable std::cout to be used without std::ostream being declared.

std::ostream is just a typedef. So std::cout can be declared as
being of the real underlying type.

>>Anyway, my #inclusion of <ostream>
>>in the code was not for 'std::ostream', but for 'std::endl'.
>>
>>You seem to be advocating dependence upon a non-required
>>implementation strategy. I don't do that. Of course
>>you're free to do so if you like. But were you to write
>>such code for me, I would reject it.
>>
>>
>>>Not to mention all the code that would break.
>>
>>That would *not* be the fault of the language or library,
>>but of the code.
>
>
> But the language could safely be charged with being complicit in the crime.

A reasonable accusation.

>>Such code itself is already 'broken',
>>it's simply taking advantage of an (admittedly common)
>>implementation method. Depending upon nonrequired
>>implementation methods is imo not a good idea.
>>
>>
>>>You might well be
>>>the only programmer on the planet who includes those headers explictly.
>>
>>Of course I won't let my code depend upon implicit
>>behavior (however ubiquitous) which is not required.
>>If I'm alone in this, so be it.
>>
>>When I write code, I strive for correctness and maximum
>>portability (including to implementations not yet created),
>>not company or consensus.
>
>
> I'm sure you're right about the standard, and therefore you are also right
> to point it out. However, those who prepared the standard were quite
> unrealistic in their expectations.

You ought not to assume things about what the committee's expectations
were; instead entertain the idea that the current situation may have
been a compromise, not the best that people could conceive of.

-- James

James Dennett

unread,
Dec 17, 2004, 12:03:31 AM12/17/04
to
David White wrote:

However it liked -- why assume anything? It could have included
a private header, also included from <ostream>, which does nothing
but define the class and the std::ostream typedef.

-- James

Gary Labowitz

unread,
Dec 17, 2004, 12:28:06 AM12/17/04
to
"James Dennett" <jden...@acm.org> wrote in message
news:MHtwd.66020$Af.4711@fed1read07...
<<big snip>>

> > Not to mention all the code that would break. You might well be
> > the only programmer on the planet who includes those headers explictly.
>
> No. He's not alone. But you do have a point; strict implementations
> have existed, and have mostly been changed to allow sloppier coding.

Well, you can (and did) call it "sloppier" but what it all comes down to is
a "de facto" standard that any compiler maker ignores at his peril. Too much
code relies on iostream pulling in the implied declarations that would all
break using a "strict" compiler.
It is like the time one auto manufacturer tried to move the gear shift lever
to the panel using push buttons. That dog didn't hunt, and neither would
forcing strict compliance of header purity.
If it had only started out right no one would care. What's one more include
in a program. Mostly I program with a framework that I just insert when
starting a program. But once one compiler included ios as a convenience,
it's pretty hard to get rid of it.
--
Gary


David White

unread,
Dec 17, 2004, 2:47:31 AM12/17/04
to
"James Dennett" <jden...@acm.org> wrote in message
news:8Mtwd.66023$Af.33838@fed1read07...

> David White wrote:
> > And how did <iostream> manage to include the class definition of
> > std::ostream without including <ostream>?
>
> However it liked -- why assume anything?

Of course! If you want to work with ostreams, include <ostream>. If you want
to work with cout, include <iostream>. cout is an ostream that can do
everything other ostreams can do. However, one should not assume that cout
requires the presence of <ostream>. Silly of me!

DW

James Dennett

unread,
Dec 17, 2004, 3:11:32 AM12/17/04
to
David White wrote:

There is a real lesson here, aside from jokes: don't assume
that implementations of C++ (particularly the library) are
bound by the same rules that apply to other C++ code. Standard
library implementations are special things, and they stand on
the other side of the contract that is the C++ standard from
regular user code.

-- James

Christo

unread,
Dec 17, 2004, 3:19:43 AM12/17/04
to

"Mike Wahler" <mkwa...@mkwahler.net> wrote in message
news:Q_pwd.1487$9j5...@newsread3.news.pas.earthlink.net...

> "Christo" <ch...@juststuffd.co.uk> wrote in message
> news:32en18F...@individual.net...
>>
>> "Mike Wahler" <mkwa...@mkwahler.net> wrote in message
>> news:94nwd.1291$9j5....@newsread3.news.pas.earthlink.net...
>> > Which (C and/or C++) book(s) are you reading which
>> > do not explain this?
>> >
>> > -Mike
>> >
>> >
>>
>> thanks for the help
>>
>> i am currently reading "essence of c++"
>
> I'm not familiar with that one, so I cannot comment upon
> its quality. May I ask the author and publication date?

yeah sure

actual title

"the essence of" programming using c++

published by the essence of computing

author Douglas Bell

ISBN

0-13-206186-4

Francis Glassborow

unread,
Dec 17, 2004, 4:09:41 AM12/17/04
to
In article <V_qwd.678$i6....@nasal.pacific.net.au>, David White
<n...@email.provided> writes

>And how did <iostream> manage to include the class definition of
>std::ostream without including <ostream>?

By placing the necessary definitions and declarations in an auxiliary
header that is included into both iostream and ostream.


--
Francis Glassborow ACCU
Author of 'You Can Do It!' see http://www.spellen.org/youcandoit
For project ideas and contributions: http://www.spellen.org/youcandoit/projects

Francis Glassborow

unread,
Dec 17, 2004, 4:07:32 AM12/17/04
to
In article <Dkqwd.673$i6....@nasal.pacific.net.au>, David White
<n...@email.provided> writes

>"Mike Wahler" <mkwa...@mkwahler.net> wrote in message
>news:qRpwd.1483$9j5....@newsread3.news.pas.earthlink.net...
>> "David White" <n...@email.provided> wrote in message
>> news:Yvpwd.671$i6....@nasal.pacific.net.au...
>> > Well, that's preposterous.
>>
>> If you feel that way, then take it up with ISO.
>
>It should be taken up with ISO. If what you say is true, and I don't doubt
>that it is, the standard should have anticipated that people naturally
>include headers only until their code compiles. Therefore, to ensure that
>code complies with the standard, they should have insisted that implementors
>ensure that every reference to a definition in std:: be undefined unless the
>specific header containing that definition is explicitly #included. By not
>doing this, the standard effectively guarantees that most code won't comply
>with the standard. It's all very well to say that it's not the standard's
>fault, but any standard that doesn't allow for normal behaviour isn't very
>useful as a standard.

Those responsible for the C++ Standard are not idiots, a great number of
then are active in software development. So rather than saying what you
think they should have done, you should ask why it is the way it is.

One important guideline for all Standards is that they should not, if
avoidably, mandate implementation, only semantics.

A large part of the C++ Library is based on templates. Exactly what a
specific implementation of a template requires to be visible is
implementation dependent. After a considerable number of hours by a
considerable number of expert library designers and implementors, WG21
reached the conclusion that it was not possible to specify the maximum
contents of many of the standard headers without unreasonably imposing
on implementors.

The only correct way for a developer using C++ is to include those
headers that provide the declarations his code requires. In some cases a
smaller set of headers from a particular implementation may prove
adequate but that does not exonerate the professional from ensuring that
s/he has included what is necessary rather than just what proves to be
sufficient.

While many implementors do include ostream in their iostream header
every competent professional knows that iostream is only required to
declare eight objects. Those declarations require that definitions of
the istream, ostream, wistream and wostream be available. Those four
types are specialisations of templates.

One perfectly reasonable implementation would be to provide
implementations specific header that provides the necessary type
definitions which is included into any standard header that requires
those definitions. In the case of iostream and ostream, both require
common definitions which could be factored out into such an auxiliary
header (and by doing so avoid including more declarations into a users
code than were strictly necessary).

David White

unread,
Dec 17, 2004, 4:15:49 AM12/17/04
to
"James Dennett" <jden...@acm.org> wrote in message
news:MHtwd.66020$Af.4711@fed1read07...

> No. He's not alone. But you do have a point; strict implementations
> have existed, and have mostly been changed to allow sloppier coding.

Sloppier coding? I'd say logical, sensible coding. How many people have ever
implemented a class hiercharchy that didn't assume that inclusion of the
header for a derived class would pull in the header that one would include
for its base class?

Perhaps this suggestion is heretical, but, in the interests of common sense
and consistency, wouldn't it have been better if the standard had specified
that <iostream> _always_ pulls in <ostream> and <ios>? Since you include
<ostream> whenever you use an object declared as an ostream, why _shouldn't_
it be pulled in when you include the header for the particular ostream cout?

DW

Francis Glassborow

unread,
Dec 17, 2004, 4:18:18 AM12/17/04
to
In article <k-qdncKwUYU...@comcast.com>, Gary Labowitz
<glab...@comcast.net> writes


That is the wrong way round. We do not fix the standard to accommodate
bad or sloppy code.

WG21 is giving serious consideration to #include <all> for the benefit
of programmers who either do not care, or cannot be bothered to
determine which headers they need.

Francis Glassborow

unread,
Dec 17, 2004, 4:14:19 AM12/17/04
to
In article <qwwwd.66042$Af.46731@fed1read07>, James Dennett
<jden...@acm.org> writes

>There is a real lesson here, aside from jokes: don't assume
>that implementations of C++ (particularly the library) are
>bound by the same rules that apply to other C++ code. Standard
>library implementations are special things, and they stand on
>the other side of the contract that is the C++ standard from
>regular user code.

But is that actually the case here? Most of us know that refactoring
reduces over all complexity. The use of the 'obvious' #include <ostream>
in iostream brings in more declarations/definitions than are needed. Why
should WG21 be criticised because they allow both the trivial
implementation and a more sophisticated refactored one where the common
requirements of iostream and ostream are placed in a distinct header.

Chris ( Val )

unread,
Dec 17, 2004, 4:55:40 AM12/17/04
to

"David White" <n...@email.provided> wrote in message
news:evxwd.698$i6....@nasal.pacific.net.au...

| "James Dennett" <jden...@acm.org> wrote in message
| news:MHtwd.66020$Af.4711@fed1read07...
| > No. He's not alone. But you do have a point; strict implementations
| > have existed, and have mostly been changed to allow sloppier coding.
|
| Sloppier coding? I'd say logical, sensible coding. How many people have ever
| implemented a class hiercharchy that didn't assume that inclusion of the
| header for a derived class would pull in the header that one would include
| for its base class?
|
| Perhaps this suggestion is heretical, but, in the interests of common sense
| and consistency, wouldn't it have been better if the standard had specified
| that <iostream> _always_ pulls in <ostream> and <ios>?

Imo, no.

I think it would have been much better, if C++ could have been
designed to follow the 'C' inclusion rules. I would much rather
that my compiler told me I had a header missing, and aborted
it's compiling phase, upon such discovery.

| Since you include <ostream> whenever you use an object declared
| as an ostream, why _shouldn't_ it be pulled in when you include
| the header for the particular ostream cout?

Why should it ?

C++ also tries to abide by the adage, that you shouldn't
be penalised (or pay) for something you don't use.

Cheers.
Chris Val


Ben Cottrell

unread,
Dec 17, 2004, 5:27:40 AM12/17/04
to
Francis Glassborow wrote:

> WG21 is giving serious consideration to #include <all> for the benefit
> of programmers who either do not care, or cannot be bothered to
> determine which headers they need.

That sounds like a bad idea to me. Shouldn't WG21 be trying to
encourage good habits for new and seasoned programmers alike?
While including the entire standard library in a "hello world" program
doesn't have any ill effects, it's a poor habit to get into once you are
past the initial stage of learning the basics IMHO. Habits like that
don't shake off very easily either once you have adopted them.

--
Ben Cottrell AKA Bench

Francis Glassborow

unread,
Dec 17, 2004, 6:33:22 AM12/17/04
to
In article <32footF...@individual.net>, "Chris ( Val )"
<chri...@bigpond.com.au> writes

>I think it would have been much better, if C++ could have been
>designed to follow the 'C' inclusion rules. I would much rather
>that my compiler told me I had a header missing, and aborted
>it's compiling phase, upon such discovery.

And had that been actually possible we would have done it. It isn't, and
unlike C, C++ does not have the option of providing declarations in
multiple headers. C++ needs definitions and placing the same definition
in more than one header files results in redefinition errors.

The alternative is to provide hundreds of headers and expect the
programmer to include dozens of them for even a simple program.

Alwyn

unread,
Dec 17, 2004, 7:57:36 AM12/17/04
to
On Fri, 17 Dec 2004 01:59:00 +0000, Mike Wahler wrote:

> "Alwyn" <al...@blueyonder.co.uk> wrote in message
> news:pan.2004.12.17....@blueyonder.co.uk...
>> On Fri, 17 Dec 2004 01:24:24 +0000, Mike Wahler wrote:
>>
>> >
>> > "Alwyn" <al...@blueyonder.co.uk> wrote in message
>> > news:pan.2004.12.17...@blueyonder.co.uk...
>> >> On Fri, 17 Dec 2004 00:52:12 +0000, Mike Wahler wrote:
>> >> >
>> >> > Anyway, I also don't take Josuttis or L&K as the ultimate
>> >> > authority. I take ISO.
>> >>
>> >> OK, guess where this little example comes from:
>> >
>> > Doesn't matter. It's not 100% conformant, regardless
>> > the source. When I said I get my 'usage rules' from
>> > ISO, I meant the ISO 14882 document, not anything
>> > I see that might have "ISO" attached to it.
>>
>> That was from the 1997 Public Review document. Are you telling us that
>> that example does not occur in the ISO document?
>
> No I'm not.
>
>> Or maybe they changed it
>
> Doesn't matter. It's a *example*, it does not comprise
> a requirement, constraint, etc. Also it's well known
> that the standard document isn't perfect. But I certainly
> won't let my code depend upon behavior not explicitly
> mandated by the standard.

<snort>

When one sees code quoted in a standards report, it would be reasonable to
expect it to conform to the standards that document stipulates, unless it
is explicitly marked othewise.

We've come to a pretty pass, haven't we, when the standardisers themselves
seem not to be able to write standards-conforming code!


Alwyn

Gary Labowitz

unread,
Dec 17, 2004, 9:01:42 AM12/17/04
to
"Francis Glassborow" <fra...@robinton.demon.co.uk> wrote in message
news:NN9MNAFa...@robinton.demon.co.uk...

> In article <k-qdncKwUYU...@comcast.com>, Gary Labowitz
> <glab...@comcast.net> writes
> That is the wrong way round. We do not fix the standard to accommodate
> bad or sloppy code.

Come on, now, Francis, you know I didn't suggest that. Of course the
standard stays the same. But it doesn't disallow compiler extensions does
it? And this could just be considered header extensions. Do I like it? No.
Is it going to happen? Yes. Are those who know what's going on be able to
make code work? Yes. The small annoyance of this thread turns out to be the
annoyance of one person disliking the coding style of another based on the
compiler being used. We all have to get over it.
On the other hand, that <all> header sounds like a worse cure than the
problem ever is. Vote no on <all>.
--
Gary


Francis Glassborow

unread,
Dec 17, 2004, 10:22:27 AM12/17/04
to
In article <pan.2004.12.17....@blueyonder.co.uk>, Alwyn
<al...@blueyonder.co.uk> writes

>We've come to a pretty pass, haven't we, when the standardisers themselves
>seem not to be able to write standards-conforming code!

You mean when they show themselves to be human? Come on, let us have a
little understanding.

James Dennett

unread,
Dec 17, 2004, 10:59:57 AM12/17/04
to
Ben Cottrell wrote:

The "cost" of this "bad habit" is usually very low; the cost of
having to get the right headers is higher. Good language standards
respect economics.

But we're drifting off-topic; comp.std.c++ is the place for this.

-- James

Alwyn

unread,
Dec 17, 2004, 4:19:39 PM12/17/04
to
On Fri, 17 Dec 2004 15:22:27 +0000, Francis Glassborow wrote:
>
> In article <pan.2004.12.17....@blueyonder.co.uk>, Alwyn
> <al...@blueyonder.co.uk> writes
>>We've come to a pretty pass, haven't we, when the standardisers themselves
>>seem not to be able to write standards-conforming code!
>
> You mean when they show themselves to be human? Come on, let us have a
> little understanding.

Am I the one who fails to show understanding when one poster
here criticises another's code for 'mistakes' that have been perpetrated
or encouraged by, among others, N. Josuttis, A. Koenig and B. Moo, A.
Langer and K. Kreft, P.J. Plauger, B, Stroustrup and the collective
authorship of the C++ public draft standard? (In this last case, perhaps
the most telling of all, I still don't know whether this has been
corrected in the final version or whether a defect report has been entered
against it.)

My point is: What hope does the ordinary user of C++ have of writing
standards-conforming code when those acknowledged as the highest
authorities are, to use your word, 'sloppy' in this regard?


Alwyn

Mike Wahler

unread,
Dec 17, 2004, 5:06:43 PM12/17/04
to

"Alwyn" <al...@blueyonder.co.uk> wrote in message
news:pan.2004.12.17....@blueyonder.co.uk...

Here's my take on all this. No human being is (or can be) perfect.
I take my 'guidance' from 'gurus' such as those you cited, but use
ISO 14882 as the final arbiter for correctness. I know that virtually
everyone concerned realizes that even the standard itself isn't perfect,
so when unsure about a particular issue, I'll ask specific questions
about it here and perhaps at comp.std.c++

I really didn't expect my 'corrections' to generate such a
firestorm of controversy. My intention was certainly not
to offend anyone, my apologies to anyone who feels I have.

-Mike

Chris ( Val )

unread,
Dec 17, 2004, 7:27:38 PM12/17/04
to

"Francis Glassborow" <fra...@robinton.demon.co.uk> wrote in message
news:wOrztxSC...@robinton.demon.co.uk...

| In article <32footF...@individual.net>, "Chris ( Val )"
| <chri...@bigpond.com.au> writes
| >I think it would have been much better, if C++ could have been
| >designed to follow the 'C' inclusion rules. I would much rather
| >that my compiler told me I had a header missing, and aborted
| >it's compiling phase, upon such discovery.
|
| And had that been actually possible we would have done it.

I don't doubt that at all, and can understand that there
are constraints to deal with.

| It isn't, and unlike C, C++ does not have the option of providing
| declarations in multiple headers. C++ needs definitions and placing
| the same definition in more than one header files results in
| redefinition errors.

Yes, I understand that.

| The alternative is to provide hundreds of headers and expect the
| programmer to include dozens of them for even a simple program.

I would prefer that the programmer had control over what is and what
is not included, given that it would be easy enough for compilers to
diagnose what header is missing, should it (rarely :-)) occur.

Cheers.
Chris Val

Alwyn

unread,
Dec 17, 2004, 7:49:00 PM12/17/04
to
On Sat, 18 Dec 2004 11:27:38 +1100, Chris ( Val ) wrote:
>
> I would prefer that the programmer had control over what is and what
> is not included, given that it would be easy enough for compilers to
> diagnose what header is missing, should it (rarely :-)) occur.

We can do a lot better than that these days. Get rid of the preprocessor.
Headers are compiled and indexed. No more need for '#include'. When you
use something it doesn't already know about, the compiler looks for it and
tries to bring it in.


Alwyn

Chris ( Val )

unread,
Dec 17, 2004, 7:58:14 PM12/17/04
to

"Alwyn" <al...@blueyonder.co.uk> wrote in message
news:pan.2004.12.18....@blueyonder.co.uk...

My suggestion was in opposition to:

"The alternative is to provide hundreds of headers and expect the
programmer to include dozens of them for even a simple program"

...written by Francis.

Your suggestion is of course an ideal one, if it could be
implemented into the language proper without too much headache.

Cheers.
Chris Val


Mike Wahler

unread,
Dec 17, 2004, 8:07:46 PM12/17/04
to

"Chris ( Val )" <chri...@bigpond.com.au> wrote in message
news:32hdl5F...@individual.net...

But imo headers don't belong as part of the language proper.
They declare library entities.

While not 'perfect', I find the existing state of affairs
concerning standard headers to be quite usable.

-Mike


Alwyn

unread,
Dec 17, 2004, 8:10:18 PM12/17/04
to
On Sat, 18 Dec 2004 11:58:14 +1100, Chris ( Val ) wrote:
>
> Your suggestion is of course an ideal one, if it could be
> implemented into the language proper without too much headache.

It's not as if it's new technology. Precompiled headers exist, and
indexing is common practice among today's IDEs. We have namespaces to
disambiguate names. It is indeed ideal: it saves both build time and
programmer time. Above all, it gets us out of the mess we're now in.


Alwyn

Chris ( Val )

unread,
Dec 17, 2004, 8:18:38 PM12/17/04
to

"Mike Wahler" <mkwa...@mkwahler.net> wrote in message
news:CpLwd.2240$9j5....@newsread3.news.pas.earthlink.net...

To be honest, I didn't really think about it too much, because
I am admittedly fully unaware of what the ramifications of this
approach might be - that's why I said "if it could be...".

I take your point though :-)

| While not 'perfect', I find the existing state of affairs
| concerning standard headers to be quite usable.

So do I - It's just that I think the 'C' rules are better,
in that there is no ambiguity about what is or needs to be
included.

Cheers.
Chris Val


Chris ( Val )

unread,
Dec 17, 2004, 8:27:05 PM12/17/04
to

"Alwyn" <al...@blueyonder.co.uk> wrote in message
news:pan.2004.12.18...@blueyonder.co.uk...

Ok, I know they have existed for a while, and even my
compiler manufacturer uses them - I use them implicitly.

Now, let's say you're right - Then what :-) ?

How do we fix it ?, who will fix it ?, who will implement
it ?, who is willing to put in the time and effort to bring
it to fruition ?

I'm sure anything could be done with a lot of collaboration,
but look how long it takes to get even seemingly simple things
into the language.

Cheers.
Chris Val


Alwyn

unread,
Dec 17, 2004, 8:31:24 PM12/17/04
to
On Sat, 18 Dec 2004 12:27:05 +1100, Chris ( Val ) wrote:
>
> How do we fix it ?, who will fix it ?, who will implement
> it ?, who is willing to put in the time and effort to bring
> it to fruition ?

A compiler vendor could provide it as an extension. If it proves popular,
other vendors might want to try it also in order to be competitive.

> I'm sure anything could be done with a lot of collaboration, but look
> how long it takes to get even seemingly simple things into the language.

It should be much easier to get things standardised if you've already got
a working implementation which shows merit.


Alwyn

Chris ( Val )

unread,
Dec 17, 2004, 8:42:35 PM12/17/04
to

"Alwyn" <al...@blueyonder.co.uk> wrote in message
news:pan.2004.12.18....@blueyonder.co.uk...

| On Sat, 18 Dec 2004 12:27:05 +1100, Chris ( Val ) wrote:
| >
| > How do we fix it ?, who will fix it ?, who will implement
| > it ?, who is willing to put in the time and effort to bring
| > it to fruition ?
|
| A compiler vendor could provide it as an extension. If it proves popular,
| other vendors might want to try it also in order to be competitive.

But this has already been happening amongst many compiler
manufactures. I don't know for how long it has been happening,
but I would assume that it has been quite a number of years.

| > I'm sure anything could be done with a lot of collaboration, but look
| > how long it takes to get even seemingly simple things into the language.
|
| It should be much easier to get things standardised if you've already got
| a working implementation which shows merit.

Like above though, if it has been in major compilers for years
already, then it must and does have merit, but merit alone does
not seem to be enough to make a change to the standard, well not
yet anyway :-)

How would removing the pre-processor for example, fit in with the
backwards compatibility model ?

I have to run off, but I'll be back later.

Cheers.
Chris Val


Alwyn

unread,
Dec 17, 2004, 9:40:44 PM12/17/04
to
On Sat, 18 Dec 2004 12:42:35 +1100, Chris ( Val ) wrote:
>
> "Alwyn" <al...@blueyonder.co.uk> wrote in message
> news:pan.2004.12.18....@blueyonder.co.uk...
> | On Sat, 18 Dec 2004 12:27:05 +1100, Chris ( Val ) wrote:
> | >
> | > How do we fix it ?, who will fix it ?, who will implement
> | > it ?, who is willing to put in the time and effort to bring
> | > it to fruition ?
> |
> | A compiler vendor could provide it as an extension. If it proves popular,
> | other vendors might want to try it also in order to be competitive.
>
> But this has already been happening amongst many compiler
> manufactures. I don't know for how long it has been happening,
> but I would assume that it has been quite a number of years.

What? You mean precompiled headers? Almost everybody provides them these
days as a conforming extension. (The GCC implementation is broken, by the
way.) So far as I can see, there is no current need for the standard to
say anything about them.

> | > I'm sure anything could be done with a lot of collaboration, but
> | > look how long it takes to get even seemingly simple things into the
> | > language.
> |
> | It should be much easier to get things standardised if you've already
> | got a working implementation which shows merit.
>
> Like above though, if it has been in major compilers for years already,
> then it must and does have merit, but merit alone does not seem to be
> enough to make a change to the standard, well not yet anyway :-)

I don't know of any C++ compiler that implements what I've suggested.
Compilers for many other languages are already doing something similar,
however.

Getting things done by a committee needs old-fashioned salesmanship and
politicking. Make sure everybody knows and understands what you're on
about; promote your views incessantly. Tell people you'll support their
proposal if they support yours. Appear to show flexibility where
necessary; smile a lot and give the impression you're all sweetness and
light. Pack meetings with your supporters. Get some 'big guns' on your
side (Stroustrup is known to detest the preprocessor). Investigate
people's private lives with a view to character assassination and
blackmail. In short, be prepared to be thoroughly unscrupulous in pursuit
of the greater good of programmerkind.

Of course, having a sound and well thought out proposal with a working
(prototype) implementation can also be of some help, but experience
has shown that that is by no means the first consideration.

> How would removing the pre-processor for example, fit in with the
> backwards compatibility model ?

You can't get rid of it straight away. You extend the compiler to
implement some of its features. After many years, it gets 'deprecated'.
Allow a century or so to pass, and then it can then be quietly dropped. If
people need a macro processor, there are better ones around.


Alwyn

Francis Glassborow

unread,
Dec 18, 2004, 5:55:16 AM12/18/04
to
In article <pan.2004.12.18...@blueyonder.co.uk>, Alwyn
<al...@blueyonder.co.uk> writes

>It's not as if it's new technology. Precompiled headers exist, and
>indexing is common practice among today's IDEs. We have namespaces to
>disambiguate names. It is indeed ideal: it saves both build time and
>programmer time. Above all, it gets us out of the mess we're now in.

So why the objections being made to WG21 creating an <all> header, which
in practice would provide exactly this facility? (Users providing their
own version all.h by including all the standard headers do not get that
advantage because the compiler would not be tuned to use it without
dragging in everything regardless)

Alwyn

unread,
Dec 18, 2004, 7:05:31 AM12/18/04
to
On Sat, 18 Dec 2004 10:55:16 +0000, Francis Glassborow wrote:

> In article <pan.2004.12.18...@blueyonder.co.uk>, Alwyn
> <al...@blueyonder.co.uk> writes
>>It's not as if it's new technology. Precompiled headers exist, and
>>indexing is common practice among today's IDEs. We have namespaces to
>>disambiguate names. It is indeed ideal: it saves both build time and
>>programmer time. Above all, it gets us out of the mess we're now in.
>
> So why the objections being made to WG21 creating an <all> header, which
> in practice would provide exactly this facility? (Users providing their
> own version all.h by including all the standard headers do not get that
> advantage because the compiler would not be tuned to use it without
> dragging in everything regardless)

As I recall, there were only two objectors, neither of whom gave a
coherent reason for his preference. Perhaps they did not appreciate that
the facility you mentioned consisted of something other than just
appending together each header from the standard library.

One of the greatest problems I experience with current C++ implementations
is that compilation can be extremely slow on account of having to process
many headers. I'm sure that anything that helps to speed up compilation
will be welcomed by a lot of people.


Alwyn

Gary Labowitz

unread,
Dec 18, 2004, 8:38:41 AM12/18/04
to
"Alwyn" <al...@blueyonder.co.uk> wrote in message
news:pan.2004.12.18....@blueyonder.co.uk...
> On Sat, 18 Dec 2004 10:55:16 +0000, Francis Glassborow wrote:
>
> > In article <pan.2004.12.18...@blueyonder.co.uk>, Alwyn
> > <al...@blueyonder.co.uk> writes
> >>It's not as if it's new technology. Precompiled headers exist, and
> >>indexing is common practice among today's IDEs. We have namespaces to
> >>disambiguate names. It is indeed ideal: it saves both build time and
> >>programmer time. Above all, it gets us out of the mess we're now in.
> >
> > So why the objections being made to WG21 creating an <all> header, which
> > in practice would provide exactly this facility? (Users providing their
> > own version all.h by including all the standard headers do not get that
> > advantage because the compiler would not be tuned to use it without
> > dragging in everything regardless)
>
> As I recall, there were only two objectors, neither of whom gave a
> coherent reason for his preference. Perhaps they did not appreciate that
> the facility you mentioned consisted of something other than just
> appending together each header from the standard library.

I was one of those who said 'no' to <all>.
Two points: first, I don't like the idea of the compiler getting things "as
needed" in one statement. It would become hard to get specific headers that
I want (say from a test library) and also get defaults from other libraries.
The order of headers would become an issue, I think.
Second, I misunderstood that only headers that were needed would be brought
in. How that would be done I can't envision, especially when functions live
in various libraries. I was thinking the <all> header would just bring in
everything. And that is not good.
Java's import declarations and definitions seems to be a fairly reasonable
approach for selecting the libraries to be used. But note that the import
order is significant in Java, a downside in my opinion. Of course, all code
is order dependent, so maybe it's not such a big deal after all. [Also note,
and be sure to do so, that the import is not the same as includes. I know
this and you should, too. I am refering to the package selection mechanism
of Java NOT include-like operation.]
--
Gary


B. v Ingen Schenau

unread,
Dec 18, 2004, 11:21:21 AM12/18/04
to
Alwyn wrote:

> Am I the one who fails to show understanding when one poster
> here criticises another's code for 'mistakes' that have been
> perpetrated or encouraged by, among others, N. Josuttis, A. Koenig and
> B. Moo, A. Langer and K. Kreft, P.J. Plauger, B, Stroustrup and the
> collective authorship of the C++ public draft standard? (In this last
> case, perhaps the most telling of all, I still don't know whether this
> has been corrected in the final version or whether a defect report has
> been entered against it.)

The code you posted from the latest draft of the standard is also
present in the 2003 edition of the standard itself (clause
27.6.1.3p22).
There is not a defect report specifically against this example, but
there is a more general defect report about the issue of which headers
are automatically included in other headers (DR #343), which has been
classified as 'NAD, Future' (Not-A-Defect, re-examine when preparing
the next revision).

>
> My point is: What hope does the ordinary user of C++ have of writing
> standards-conforming code when those acknowledged as the highest
> authorities are, to use your word, 'sloppy' in this regard?

None at all.
Technically, the issue is even worse because to use std::string or
std::vector, you need *two* headers.
You need <string> or <vector> for the template that you want to use, and
besides that you need <memory> for the allocator that is implicitly
used by both for the memory management.

IOW, this program may fail to compile (although I doubt that it will
fail on any current compiler):

#include <string>
int main()
{
std::string s = "Hello World!";
}

>
>
> Alwyn

Bart v Ingen Schenau
--
a.c.l.l.c-c++ FAQ: http://www.comeaucomputing.com/learn/faq
c.l.c FAQ: http://www.eskimo.com/~scs/C-faq/top.html
c.l.c++ FAQ: http://www.parashift.com/c++-faq-lite/

James Dennett

unread,
Dec 18, 2004, 11:33:15 AM12/18/04
to
Gary Labowitz wrote:

> "Alwyn" <al...@blueyonder.co.uk> wrote in message
> news:pan.2004.12.18....@blueyonder.co.uk...
>
>>On Sat, 18 Dec 2004 10:55:16 +0000, Francis Glassborow wrote:
>>
>>
>>>In article <pan.2004.12.18...@blueyonder.co.uk>, Alwyn
>>><al...@blueyonder.co.uk> writes
>>>
>>>>It's not as if it's new technology. Precompiled headers exist, and
>>>>indexing is common practice among today's IDEs. We have namespaces to
>>>>disambiguate names. It is indeed ideal: it saves both build time and
>>>>programmer time. Above all, it gets us out of the mess we're now in.
>>>
>>>So why the objections being made to WG21 creating an <all> header, which
>>>in practice would provide exactly this facility? (Users providing their
>>>own version all.h by including all the standard headers do not get that
>>>advantage because the compiler would not be tuned to use it without
>>>dragging in everything regardless)
>>
>>As I recall, there were only two objectors, neither of whom gave a
>>coherent reason for his preference. Perhaps they did not appreciate that
>>the facility you mentioned consisted of something other than just
>>appending together each header from the standard library.
>
>
> I was one of those who said 'no' to <all>.
> Two points: first, I don't like the idea of the compiler getting things "as
> needed" in one statement.

Maybe there are two different things being discussed here;
the <all> header discussed by the committee doesn't require
any language changes or new compiler facilities, though it
could bring faster compilation through helping with precompiled
header use. It's just there to be equivalent to including all
standard library headers.

> It would become hard to get specific headers that
> I want (say from a test library) and also get defaults from other libraries.
> The order of headers would become an issue, I think.

I think with <all> as discussed above, those are non-issues.

> Second, I misunderstood that only headers that were needed would be brought
> in. How that would be done I can't envision, especially when functions live
> in various libraries. I was thinking the <all> header would just bring in
> everything. And that is not good.

Please give reasons for that. Why would having the whole
standard library accessible from a single header not be
good? Consider how many programs it would simplify significantly,
and how much easier it would make it for many people to write
correct code -- and then maybe describe the costs you perceive
to explain how they outweigh the benefits, if you would be so
kind.

-- James

Alwyn

unread,
Dec 18, 2004, 2:46:35 PM12/18/04
to
On Sat, 18 Dec 2004 08:38:41 -0500, Gary Labowitz wrote:
>
> Second, I misunderstood that only headers that were needed would be brought
> in. How that would be done I can't envision, especially when functions live
> in various libraries. I was thinking the <all> header would just bring in
> everything. And that is not good.

But aren't you the one who wrote:

> Mostly I program with a framework that I just insert when
> starting a program.

That's what I do too:

#include <Carbon/Carbon>

for the low-level C API or (in Objective-C)

#import <Cocoa/Cocoa>

for a vast object-oriented framework, and I've never heard anyone complain
about it; it just works. How is the C++ standard library any different?


Alwyn

David White

unread,
Dec 18, 2004, 3:47:43 PM12/18/04
to
"Chris ( Val )" <chri...@bigpond.com.au> wrote in message
news:32footF...@individual.net...

>
> "David White" <n...@email.provided> wrote in message
> news:evxwd.698$i6....@nasal.pacific.net.au...
> | Perhaps this suggestion is heretical, but, in the interests of common
sense
> | and consistency, wouldn't it have been better if the standard had
specified
> | that <iostream> _always_ pulls in <ostream> and <ios>?
>
> Imo, no.
>
> I think it would have been much better, if C++ could have been
> designed to follow the 'C' inclusion rules. I would much rather
> that my compiler told me I had a header missing, and aborted
> it's compiling phase, upon such discovery.
>
> | Since you include <ostream> whenever you use an object declared
> | as an ostream, why _shouldn't_ it be pulled in when you include
> | the header for the particular ostream cout?
>
> Why should it ?

Er, because to do anything useful with cout - to actually output something
for example - you have to use its ostream behaviour, and <ostream> is,
apparently, the standard header that one includes to use ostreams. Perhaps I
should be surprised that the following program works.
#include <iostream>

int main()
{
std::cout << "Hello world\n";
}

DW

Mike Wahler

unread,
Dec 18, 2004, 3:53:04 PM12/18/04
to

"David White" <n...@email.provided> wrote in message
news:RJ0xd.813$i6.1...@nasal.pacific.net.au...

> "Chris ( Val )" <chri...@bigpond.com.au> wrote in message
> news:32footF...@individual.net...
> >
> > "David White" <n...@email.provided> wrote in message
> > news:evxwd.698$i6....@nasal.pacific.net.au...
> > | Perhaps this suggestion is heretical, but, in the interests of common
> sense
> > | and consistency, wouldn't it have been better if the standard had
> specified
> > | that <iostream> _always_ pulls in <ostream> and <ios>?
> >
> > Imo, no.
> >
> > I think it would have been much better, if C++ could have been
> > designed to follow the 'C' inclusion rules. I would much rather
> > that my compiler told me I had a header missing, and aborted
> > it's compiling phase, upon such discovery.
> >
> > | Since you include <ostream> whenever you use an object declared
> > | as an ostream, why _shouldn't_ it be pulled in when you include
> > | the header for the particular ostream cout?
> >
> > Why should it ?
>
> Er, because to do anything useful with cout - to actually output something
> for example - you have to use its ostream behaviour, and <ostream> is,
> apparently, the standard header that one includes to use ostreams.

It's required if you want to refer to the ostream *type*.
For referring to the 'cout' *object*, all you need is <iostream>

> Perhaps I
> should be surprised that the following program works.
> #include <iostream>
>
> int main()
> {
> std::cout << "Hello world\n";
> }

I'm not surprised (except perhaps about the part mentioned elsethread
about that << operator being a nonmember, and not visible -- I never
had thought about that issue before).


-Mike


David White

unread,
Dec 18, 2004, 4:04:36 PM12/18/04
to
"Francis Glassborow" <fra...@robinton.demon.co.uk> wrote in message
news:6cBRJvDr...@robinton.demon.co.uk...
> In article <qwwwd.66042$Af.46731@fed1read07>, James Dennett
> <jden...@acm.org> writes
> >There is a real lesson here, aside from jokes: don't assume
> >that implementations of C++ (particularly the library) are
> >bound by the same rules that apply to other C++ code. Standard
> >library implementations are special things, and they stand on
> >the other side of the contract that is the C++ standard from
> >regular user code.
>
> But is that actually the case here? Most of us know that refactoring
> reduces over all complexity. The use of the 'obvious' #include <ostream>
> in iostream brings in more declarations/definitions than are needed.

So, every time one includes <ostream> only to do ostream output, it brings
in more declarations/definitions than are needed.
// File 1
#include <iostream>

extern void hello_world(std::ostream &);

int main()
{
std::cout << "Hello world\n";

hello_world(std::cout);
}

// File 2
#include <ostream> // Pity, includes stuff I don't need

void hello_world(std::ostream &os)
{
os << "Hello world\n";
}

DW

David White

unread,
Dec 18, 2004, 4:21:10 PM12/18/04
to
"Mike Wahler" <mkwa...@mkwahler.net> wrote in message
news:QM0xd.3775$RH4....@newsread1.news.pas.earthlink.net...

> "David White" <n...@email.provided> wrote in message
> news:RJ0xd.813$i6.1...@nasal.pacific.net.au...
> > Er, because to do anything useful with cout - to actually output
something
> > for example - you have to use its ostream behaviour, and <ostream> is,
> > apparently, the standard header that one includes to use ostreams.
>
> It's required if you want to refer to the ostream *type*.
> For referring to the 'cout' *object*, all you need is <iostream>

But cout _is_ an ostream, and all its ostream behaviour is available when
you include <iostream>. Does the standard guarantee that this program will
work?
#include <iostream>

void hello_world(std::ostream &os)
{
os << "Hello world\n";
}

int main()
{
hello_world(std::cout);
}

Am I to believe that if I include <iostream> only I can use cout's ostream
behaviour as much as I like, but I can never declare it as an ostream?

If this file contained only the hello_world function and did not refer to
cout, I would have included <ostream> instead. So, it is ridiculous that the
inclusion of <ostream> is not implied by the inclusion of <iostream>.

DW

Mike Wahler

unread,
Dec 18, 2004, 4:21:47 PM12/18/04
to

"David White" <n...@email.provided> wrote in message
news:HZ0xd.814$i6.1...@nasal.pacific.net.au...

#include <algorithm> /* includes (a large amount of) stuff I don't need */

int main()
{
int a[] = {3, 6, 5, 8};
std::sort(a, a + sizeof a / sizeof *a);
return 0;
}

Where does it end? :-)

-Mike

James Dennett

unread,
Dec 18, 2004, 4:40:28 PM12/18/04
to
David White wrote:

> "Mike Wahler" <mkwa...@mkwahler.net> wrote in message
> news:QM0xd.3775$RH4....@newsread1.news.pas.earthlink.net...
>
>>"David White" <n...@email.provided> wrote in message
>>news:RJ0xd.813$i6.1...@nasal.pacific.net.au...
>>
>>>Er, because to do anything useful with cout - to actually output
>
> something
>
>>>for example - you have to use its ostream behaviour, and <ostream> is,
>>>apparently, the standard header that one includes to use ostreams.
>>
>>It's required if you want to refer to the ostream *type*.
>>For referring to the 'cout' *object*, all you need is <iostream>
>
>
> But cout _is_ an ostream, and all its ostream behaviour is available when
> you include <iostream>.

I don't think that's true. All you have is a declaration
of an object.

> Does the standard guarantee that this program will
> work?
> #include <iostream>
>
> void hello_world(std::ostream &os)
> {
> os << "Hello world\n";
> }
>
> int main()
> {
> hello_world(std::cout);
> }

No, it does not. Though that might get changed.

> Am I to believe that if I include <iostream> only I can use cout's ostream
> behaviour as much as I like, but I can never declare it as an ostream?

<iostream> must declare it as a std::ostream, so you can
also use the type name (specifically, typedef) std::ostream.

> If this file contained only the hello_world function and did not refer to
> cout, I would have included <ostream> instead. So, it is ridiculous that the
> inclusion of <ostream> is not implied by the inclusion of <iostream>.

Your conclusion doesn't follow from anything you've said, I'm
afraid.

-- James

David White

unread,
Dec 18, 2004, 4:44:33 PM12/18/04
to
"Mike Wahler" <mkwa...@mkwahler.net> wrote in message
news:Lb1xd.3794$RH4....@newsread1.news.pas.earthlink.net...

>
> "David White" <n...@email.provided> wrote in message
> news:HZ0xd.814$i6.1...@nasal.pacific.net.au...
> > // File 1
> > #include <iostream>
> >
> > extern void hello_world(std::ostream &);
> >
> > int main()
> > {
> > std::cout << "Hello world\n";
> > hello_world(std::cout);
> > }
> >
> > // File 2
> > #include <ostream> // Pity, includes stuff I don't need
> >
> > void hello_world(std::ostream &os)
> > {
> > os << "Hello world\n";
> > }
>
> #include <algorithm> /* includes (a large amount of) stuff I don't need */
>
> int main()
> {
> int a[] = {3, 6, 5, 8};
> std::sort(a, a + sizeof a / sizeof *a);
> return 0;
> }
>
> Where does it end? :-)

Exactly. If <ostream> includes stuff you don't need when working with
ostreams in general, is it unreasonable for the same stuff to be included
when working with any specific ostream?

I guess I've missed the point of <ostream>. It's primary purpose is not for
ostreams at all. It's just there for trivial extras like std::endl.

DW

Mike Wahler

unread,
Dec 18, 2004, 5:12:53 PM12/18/04
to

"David White" <n...@email.provided> wrote in message
news:cd1xd.816$i6.1...@nasal.pacific.net.au...

> "Mike Wahler" <mkwa...@mkwahler.net> wrote in message
> news:QM0xd.3775$RH4....@newsread1.news.pas.earthlink.net...
> > "David White" <n...@email.provided> wrote in message
> > news:RJ0xd.813$i6.1...@nasal.pacific.net.au...
> > > Er, because to do anything useful with cout - to actually output
> something
> > > for example - you have to use its ostream behaviour, and <ostream> is,
> > > apparently, the standard header that one includes to use ostreams.
> >
> > It's required if you want to refer to the ostream *type*.
> > For referring to the 'cout' *object*, all you need is <iostream>
>
> But cout _is_ an ostream, and all its ostream behaviour is available when
> you include <iostream>. Does the standard guarantee that this program will
> work?

The way I read the standard, no.

> #include <iostream>
>
> void hello_world(std::ostream &os)

Undefined symbol 'std::ostream'

> {
> os << "Hello world\n";
> }
>
> int main()
> {
> hello_world(std::cout);
> }
>
> Am I to believe that if I include <iostream> only I can use cout's ostream
> behaviour as much as I like, but I can never declare it as an ostream?

Essentially yes, that's the way I see it. (Strictly speaking,
this means only invoking member functions via the 'cout' object,
but not any nonmembers, since they're not necessarily declared.)

> If this file contained only the hello_world function and did not refer to
> cout, I would have included <ostream> instead. So, it is ridiculous that
the
> inclusion of <ostream> is not implied by the inclusion of <iostream>.

Access to the features from <ostream> needed by 'cout' is indeed
implied, but not required to come from an actual #inclusion of
that header. And such access need only be granted to the 'cout'
object itself, not to the programmer. See remarks by others elsethread
about e.g. 'auxiliary, internal' headers which the impelementation has
access to, but the programmer does not. I also still maintain that
this 'internal access' method need not be via an #inclusion mechanism
at all, but however the implementor can achieve it.


-Mike


Mike Wahler

unread,
Dec 18, 2004, 5:20:11 PM12/18/04
to

"James Dennett" <jden...@acm.org> wrote in message
news:Ns1xd.701$JI.22@fed1read07...

I realize that for practical purposes, this would be the case,
but when #including <iostream>, does that really require from
a language standpoint that the name 'std::ostream' be visible
to the program? I don't see anything in the standard that
specifies this or causes me to infer such.

A Fine Mess we're in. I think I'll just go visit a 'real'
stream, drop in a line, and forget about all this for a while.
I hope it winds up being an ostream more than an istream. :-)

-Mike


Mike Wahler

unread,
Dec 18, 2004, 5:27:55 PM12/18/04
to
"David White" <n...@email.provided> wrote in message
news:6z1xd.821$i6.1...@nasal.pacific.net.au...

> "Mike Wahler" <mkwa...@mkwahler.net> wrote in message
> news:Lb1xd.3794$RH4....@newsread1.news.pas.earthlink.net...
> >
> > "David White" <n...@email.provided> wrote in message
> > news:HZ0xd.814$i6.1...@nasal.pacific.net.au...

> > > #include <ostream> // Pity, includes stuff I don't need


> > >
> > > void hello_world(std::ostream &os)
> > > {
> > > os << "Hello world\n";
> > > }
> >
> > #include <algorithm> /* includes (a large amount of) stuff I don't need
*/
> >
> > int main()
> > {
> > int a[] = {3, 6, 5, 8};
> > std::sort(a, a + sizeof a / sizeof *a);
> > return 0;
> > }
> >
> > Where does it end? :-)
>
> Exactly. If <ostream> includes stuff you don't need when working with
> ostreams in general, is it unreasonable for the same stuff to be included
> when working with any specific ostream?
>
> I guess I've missed the point of <ostream>. It's primary purpose is not
for
> ostreams at all. It's just there for trivial extras like std::endl.

I use it when I need to declare 'ostream&' parameters, e.g.
for a custom insertion operator. By #including <ostream>,
I know I have a guarantee that I have a proper declaration of this
type. With <iostream> only, I'm not convinced that I do.


-Mike


David White

unread,
Dec 18, 2004, 8:43:21 PM12/18/04
to
"James Dennett" <jden...@acm.org> wrote in message
news:Ns1xd.701$JI.22@fed1read07...
> David White wrote:
> > But cout _is_ an ostream, and all its ostream behaviour is available
when
> > you include <iostream>.
>
> I don't think that's true. All you have is a declaration
> of an object.

Yes, and the declaration is:
extern ostream cout;

It is reasonable to expect the standard to specify what I am allowed to do
with this object. For example, am I allowed to call members such as fill(),
good() etc.?

If I am, then how can calls to these members compile if the complete type is
not present? Is it even possible in C++ to write a program in which class
member functions can be called but the definition of the class to which they
belong is not present? If the class definition must be present, then it can
be used to define and use (not just declare) other objects of the class.

If I'm not allowed to call those members, where is it defined exactly what
cout can do? Am I expecting too much of cout if ask it to execute put('A')?

> <iostream> must declare it as a std::ostream, so you can
> also use the type name (specifically, typedef) std::ostream.

But not use members of std::ostream (or its underlying type), even though -
I tentatively suggest - I can use std::cout's members of std::ostream?

> > If this file contained only the hello_world function and did not refer
to
> > cout, I would have included <ostream> instead. So, it is ridiculous that
the
> > inclusion of <ostream> is not implied by the inclusion of <iostream>.
>
> Your conclusion doesn't follow from anything you've said, I'm
> afraid.

Of course it doesn't. Why would anyone expect the header <ostream>, the
standard header you use if you want to use ostreams, to have anything to do
with an ostream object?

DW

James Dennett

unread,
Dec 18, 2004, 8:51:29 PM12/18/04
to
Mike Wahler wrote:

27.3 strongly suggests it, by specifying the "synopsis" of the
header as declaring objects of type (std::)ostream and (std::)
wostream. It would seem that the intent is that those names
ought to be visible, or the header isn't really doing what the
synopsis says. But there's room for argument, if you'd like to
visit comp.std.c++... not that it's necessarilt worthwhile. It's
likely that the committee will clarify some of these issues in
any case.

-- James

David White

unread,
Dec 18, 2004, 9:17:46 PM12/18/04
to
"Mike Wahler" <mkwa...@mkwahler.net> wrote in message
news:FX1xd.2865$9j5....@newsread3.news.pas.earthlink.net...

> "David White" <n...@email.provided> wrote in message
> news:cd1xd.816$i6.1...@nasal.pacific.net.au...
> > But cout _is_ an ostream, and all its ostream behaviour is available
when
> > you include <iostream>. Does the standard guarantee that this program
will
> > work?
>
> The way I read the standard, no.
>
> > #include <iostream>
> >
> > void hello_world(std::ostream &os)
>
> Undefined symbol 'std::ostream'

My compliments to the compiler vendor who can manage to produce this error.
:-)

> > {
> > os << "Hello world\n";
> > }
> >
> > int main()
> > {
> > hello_world(std::cout);
> > }
> >
> > Am I to believe that if I include <iostream> only I can use cout's
ostream
> > behaviour as much as I like, but I can never declare it as an ostream?
>
> Essentially yes, that's the way I see it.

Crazy.

> (Strictly speaking,
> this means only invoking member functions via the 'cout' object,
> but not any nonmembers, since they're not necessarily declared.)

Hmm. I've looked at every reference to 'cout' in the standard and I can find
nothing to indicate that any of its std::ostream member functions are
available. All I can find is the declaration in <iostream>. I don't know how
one can conclude that cout's ostream members are available but ostream
itself isn't. What if a compiler vendor just did this?
namespace std
{
class basic_ostream;
typedef basic_ostream ostream;
extern ostream cout;
}

BTW, there are many examples in the standard that use std::endl without
<ostream> having been #included, not just the one that Alwyn cited earlier.
In fact, I believe that all the examples that use std::endl are wrong.

DW

David White

unread,
Dec 18, 2004, 9:53:33 PM12/18/04
to
"David White" <n...@email.provided> wrote in message
news:gz5xd.836$i6.1...@nasal.pacific.net.au...

> namespace std
> {
> class basic_ostream;
> typedef basic_ostream ostream;
> extern ostream cout;
> }

Of course, basic_ostream isn't a class, so that should be the appropriate
forward-declared form of the basic_ostream template.

DW

Chris ( Val )

unread,
Dec 19, 2004, 12:23:06 AM12/19/04
to

"Alwyn" <al...@blueyonder.co.uk> wrote in message
news:pan.2004.12.18...@blueyonder.co.uk...

| On Sat, 18 Dec 2004 12:42:35 +1100, Chris ( Val ) wrote:
| >
| > "Alwyn" <al...@blueyonder.co.uk> wrote in message
| > news:pan.2004.12.18....@blueyonder.co.uk...
| > | On Sat, 18 Dec 2004 12:27:05 +1100, Chris ( Val ) wrote:
| > | >
| > | > How do we fix it ?, who will fix it ?, who will implement
| > | > it ?, who is willing to put in the time and effort to bring
| > | > it to fruition ?
| > |
| > | A compiler vendor could provide it as an extension. If it proves popular,
| > | other vendors might want to try it also in order to be competitive.
| >
| > But this has already been happening amongst many compiler
| > manufactures. I don't know for how long it has been happening,
| > but I would assume that it has been quite a number of years.
|
| What? You mean precompiled headers?

[snip]

Yes, that is what we have been discussing.

| > Like above though, if it has been in major compilers for years already,
| > then it must and does have merit, but merit alone does not seem to be
| > enough to make a change to the standard, well not yet anyway :-)
|
| I don't know of any C++ compiler that implements what I've suggested.

I was talking about precompiled headers.

| Compilers for many other languages are already doing something similar,
| however.
|
| Getting things done by a committee needs old-fashioned salesmanship and
| politicking. Make sure everybody knows and understands what you're on
| about; promote your views incessantly. Tell people you'll support their
| proposal if they support yours. Appear to show flexibility where
| necessary; smile a lot and give the impression you're all sweetness and
| light. Pack meetings with your supporters. Get some 'big guns' on your
| side (Stroustrup is known to detest the preprocessor). Investigate
| people's private lives with a view to character assassination and
| blackmail. In short, be prepared to be thoroughly unscrupulous in pursuit
| of the greater good of programmerkind.

Sounds a little extreme :-), but, hey, it could be
happening as we speak, for all I know.

| Of course, having a sound and well thought out proposal with a working
| (prototype) implementation can also be of some help, but experience
| has shown that that is by no means the first consideration.

No doubt.

| > How would removing the pre-processor for example, fit in with the
| > backwards compatibility model ?
|
| You can't get rid of it straight away. You extend the compiler to
| implement some of its features. After many years, it gets 'deprecated'.
| Allow a century or so to pass, and then it can then be quietly dropped. If
| people need a macro processor, there are better ones around.

This falls in line with the process for progress, in today's,
current century, and that's why it takes a long time to get
something done.

Cheers.
Chris Val

James Dennett

unread,
Dec 19, 2004, 1:10:38 AM12/19/04
to
David White wrote:

> "James Dennett" <jden...@acm.org> wrote in message
> news:Ns1xd.701$JI.22@fed1read07...
>
>>David White wrote:
>>
>>>But cout _is_ an ostream, and all its ostream behaviour is available
>
> when
>
>>>you include <iostream>.
>>
>>I don't think that's true. All you have is a declaration
>>of an object.
>
>
> Yes, and the declaration is:
> extern ostream cout;
>
> It is reasonable to expect the standard to specify what I am allowed to do
> with this object.

"Reasonable" to expect, maybe, but that doesn't necessarily make
it right.

> For example, am I allowed to call members such as fill(),
> good() etc.?

No such guarantee is made by the standard.

> If I am, then how can calls to these members compile if the complete type is
> not present?

If the type definition is not visible then you can't call
member functions of that type. No exception for this case.

> Is it even possible in C++ to write a program in which class
> member functions can be called but the definition of the class to which they
> belong is not present?

No.

> If the class definition must be present, then it can
> be used to define and use (not just declare) other objects of the class.

But the definition need not be included.

> If I'm not allowed to call those members, where is it defined exactly what
> cout can do? Am I expecting too much of cout if ask it to execute put('A')?

It's an instance of type std::ostream; that determines what
can be done on it. If <ostream> is included, there's plenty
you can do.

>><iostream> must declare it as a std::ostream, so you can
>>also use the type name (specifically, typedef) std::ostream.
>
>
> But not use members of std::ostream (or its underlying type), even though -
> I tentatively suggest - I can use std::cout's members of std::ostream?

You can't rely on using std::ostream members, at all. There's
no special case for using them through one particular object.

>>>If this file contained only the hello_world function and did not refer
>
> to
>
>>>cout, I would have included <ostream> instead. So, it is ridiculous that
>
> the
>
>>>inclusion of <ostream> is not implied by the inclusion of <iostream>.
>>
>>Your conclusion doesn't follow from anything you've said, I'm
>>afraid.
>
>
> Of course it doesn't. Why would anyone expect the header <ostream>, the
> standard header you use if you want to use ostreams, to have anything to do
> with an ostream object?

Because the standard documents it that way?

-- James

Chris ( Val )

unread,
Dec 19, 2004, 3:21:03 AM12/19/04
to

"Mike Wahler" <mkwa...@mkwahler.net> wrote in message
news:QM0xd.3775$RH4....@newsread1.news.pas.earthlink.net...

|
| "David White" <n...@email.provided> wrote in message
| news:RJ0xd.813$i6.1...@nasal.pacific.net.au...
| > "Chris ( Val )" <chri...@bigpond.com.au> wrote in message
| > news:32footF...@individual.net...
| > >
| > > "David White" <n...@email.provided> wrote in message
| > > news:evxwd.698$i6....@nasal.pacific.net.au...
| > > | Perhaps this suggestion is heretical, but, in the interests of common

[snip]

| > Perhaps I
| > should be surprised that the following program works.
| > #include <iostream>
| >
| > int main()
| > {
| > std::cout << "Hello world\n";
| > }
|
| I'm not surprised (except perhaps about the part mentioned elsethread
| about that << operator being a nonmember, and not visible -- I never
| had thought about that issue before).

I remember having a discussion about the explicit inclusion
of the <ostream> header a while back with 'Russell Hanneken'
in this group.

The consensus was that the above program code is technically
wrong, for the reasons cited in this thread.

An interesting link on the matter turned up during the thread:
http://www.google.com.au/groups?q=g:thl562000961d&dq=&hl=en&lr=
&selm=d6651fb6.0301170332.d754341%40posting.google.com&rnum=19

You might need to paste both parts of the link together.

Cheers.
Chris Val


David White

unread,
Dec 19, 2004, 4:30:01 AM12/19/04
to
"James Dennett" <jden...@acm.org> wrote in message
news:1X8xd.780$JI.238@fed1read07...

> David White wrote:
> > It is reasonable to expect the standard to specify what I am allowed to
do
> > with this object.
>
> "Reasonable" to expect, maybe, but that doesn't necessarily make
> it right.

In that case you can't expect to do anything at all with <iostream> alone.

> > If I am, then how can calls to these members compile if the complete
type is
> > not present?
>
> If the type definition is not visible then you can't call
> member functions of that type. No exception for this case.

And I guess that includes the << functions as well. So, the "hello world"
program in TC++PL is not standard-conforming.

> > Is it even possible in C++ to write a program in which class
> > member functions can be called but the definition of the class to which
they
> > belong is not present?
>
> No.
>
> > If the class definition must be present, then it can
> > be used to define and use (not just declare) other objects of the class.
>
> But the definition need not be included.
>
> > If I'm not allowed to call those members, where is it defined exactly
what
> > cout can do? Am I expecting too much of cout if ask it to execute
put('A')?
>
> It's an instance of type std::ostream; that determines what
> can be done on it.

I don't know what this means. If the type definition is not present, how
does it determine what can be done with it?

> If <ostream> is included, there's plenty
> you can do.

Like output "Hello world\n" for instance?

> >>Your conclusion doesn't follow from anything you've said, I'm
> >>afraid.
> >
> >
> > Of course it doesn't. Why would anyone expect the header <ostream>, the
> > standard header you use if you want to use ostreams, to have anything to
do
> > with an ostream object?
>
> Because the standard documents it that way?

No, because from experience almost every C++ programmer on the planet,
including even those who use the examples in the standard document itself as
a guide, would expect std::ostream to be available when they include
<iostream> to use std::cout, and they would write their code accordingly. If
the standard allows <ostream> not to be present when <iostream> is included
then it is only inviting non-conforming code.

DW

Francis Glassborow

unread,
Dec 19, 2004, 4:33:22 AM12/19/04
to
In article <%25xd.833$i6.1...@nasal.pacific.net.au>, David White
<n...@email.provided> writes

>Yes, and the declaration is:
>extern ostream cout;
>
>It is reasonable to expect the standard to specify what I am allowed to do
>with this object. For example, am I allowed to call members such as fill(),
>good() etc.?

I think that for historical reasons many people do not understand the
purpose of iostream. The intention is purely to declare eight names. In
order for those declarations to be valid the compiler must be able to
see the declarations of four UDTs (istream, ostream, wistream and
wostream).

Unfortunately those four types are specialisations of four templates
each provided by its own header file. The simplest way to allow the
compiler to see declarations of those names is by including those
headers. Forward declaration of a specialisation of a template type is
not an option. Each of the four headers contain a great deal of other
material apart from that needed to declare objects of the relevant type.

Now the principle that the designers of the Standard Library might have
expected is that if the programmer was going to do output through a
(narrow) stream they would include ostream. If they were then going to
use std::cout they would include iostream whose job it is to provide the
declaration of std::cout and seven similar objects.

However, almost all implementors chose the easy route and included the
ostream header etc. in iostream with the result that the overwhelming
majority of C++ programmers came to the (false) conclusion that iostream
necessarily provided all they wanted.

Francis Glassborow

unread,
Dec 19, 2004, 4:35:08 AM12/19/04
to
In article <gz5xd.836$i6.1...@nasal.pacific.net.au>, David White
<n...@email.provided> writes

>Hmm. I've looked at every reference to 'cout' in the standard and I can find
>nothing to indicate that any of its std::ostream member functions are
>available. All I can find is the declaration in <iostream>. I don't know how
>one can conclude that cout's ostream members are available but ostream
>itself isn't. What if a compiler vendor just did this?
>namespace std
>{
> class basic_ostream;
> typedef basic_ostream ostream;
> extern ostream cout;
>}
Now rewrite that taking into account that basic_ostream is a template.

Francis Glassborow

unread,
Dec 19, 2004, 4:36:54 AM12/19/04
to
In article <Q46xd.837$i6.1...@nasal.pacific.net.au>, David White
<n...@email.provided> writes

Which is? And now you begin to see the problem. Exported templates can
help solve this problem but so far only one compiler vendor has
implemented them.

Gary Labowitz

unread,
Dec 19, 2004, 9:28:42 AM12/19/04
to
"Alwyn" <al...@blueyonder.co.uk> wrote in message
news:pan.2004.12.18....@blueyonder.co.uk...

Perhaps I misunderstand the proposed <all>. My framework (and yours, too)
just brings in a selected group of headers that I know I use most
frequently. It doesn't bring in all the standard headers. I thought that was
the "plan." Anyway, at most it slows compilation down a bit. At worst it
hides which headers are being used by what calls, and programmers could get
the wrong knowledge of how the various templates are implemented. And if I
wish to bring in a "test" header from one of my libraries, would I get
double definition ever? I guess I'd need to see the full implication of the
<all> header. It sounds like I have a misconception here.
--
Gary


James Dennett

unread,
Dec 19, 2004, 12:05:47 PM12/19/04
to
David White wrote:
> "James Dennett" <jden...@acm.org> wrote in message
> news:1X8xd.780$JI.238@fed1read07...
>
>>David White wrote:
>>
>>>It is reasonable to expect the standard to specify what I am allowed to
>
> do
>
>>>with this object.
>>
>>"Reasonable" to expect, maybe, but that doesn't necessarily make
>>it right.
>
>
> In that case you can't expect to do anything at all with <iostream> alone.

Not so; often I'd have a main function in a source file, which
might pass std::cout and possibly other streams off to functions
which takes std::ostream and/or std::istream parameters. Those
functions would be defined in other files, which would include
<ostream> and <istream> as needed but *not* <iostream> -- most
code shouldn't have an explicit dependency on the globals
std::cout, std::cerr etc.

>
>>>If I am, then how can calls to these members compile if the complete
>
> type is
>
>>>not present?
>>
>>If the type definition is not visible then you can't call
>>member functions of that type. No exception for this case.
>
>
> And I guess that includes the << functions as well. So, the "hello world"
> program in TC++PL is not standard-conforming.

Quite so, and most people do seem to view that as problematic.

>>>Is it even possible in C++ to write a program in which class
>>>member functions can be called but the definition of the class to which
>
> they
>
>>>belong is not present?
>>
>>No.
>>
>>
>>>If the class definition must be present, then it can
>>>be used to define and use (not just declare) other objects of the class.
>>
>>But the definition need not be included.
>>
>>
>>>If I'm not allowed to call those members, where is it defined exactly
>
> what
>
>>>cout can do? Am I expecting too much of cout if ask it to execute
>
> put('A')?
>
>>It's an instance of type std::ostream; that determines what
>>can be done on it.
>
>
> I don't know what this means. If the type definition is not present, how
> does it determine what can be done with it?

What is the "it" there? C++ language rules determine what
operations a type supports, depending on the declarations
and definitions that are visible. What is not determined
by the library spec is exactly which those are.

>>If <ostream> is included, there's plenty
>>you can do.
>
>
> Like output "Hello world\n" for instance?

Such great achievements, all with only two headers. :-/

>>>>Your conclusion doesn't follow from anything you've said, I'm
>>>>afraid.
>>>
>>>
>>>Of course it doesn't. Why would anyone expect the header <ostream>, the
>>>standard header you use if you want to use ostreams, to have anything to
>
> do
>
>>>with an ostream object?
>>
>>Because the standard documents it that way?
>
>
> No, because from experience almost every C++ programmer on the planet,
> including even those who use the examples in the standard document itself as
> a guide, would expect std::ostream to be available when they include
> <iostream> to use std::cout, and they would write their code accordingly. If
> the standard allows <ostream> not to be present when <iostream> is included
> then it is only inviting non-conforming code.

Arguably so.

-- James

David White

unread,
Dec 19, 2004, 4:56:08 PM12/19/04
to
"Francis Glassborow" <fra...@robinton.demon.co.uk> wrote in message
news:5yyxy7Bi...@robinton.demon.co.uk...

> Now the principle that the designers of the Standard Library might have
> expected is that if the programmer was going to do output through a
> (narrow) stream they would include ostream. If they were then going to
> use std::cout they would include iostream whose job it is to provide the
> declaration of std::cout and seven similar objects.

Well, current evidence doesn't support this theory. The examples in the
standard document and in TC++PL indicate that the who's who of C++ believed
that <iostream> was sufficient to use the std::cout object for at least <<
operations. I suspect that this whole issue was never pored over the way it
has been in this thread before the standard was written. Stroustrup and co.,
like just about everyone else, probably just assumed (or decided) that
<iostream> permitted std::cout etc. to be used for any ostream operation.
And now people are taking the standard literally and finding that it doesn't
actually give that assurance.

DW


David White

unread,
Dec 19, 2004, 5:42:56 PM12/19/04
to
"James Dennett" <jden...@acm.org> wrote in message
news:exixd.1810$JI.1233@fed1read07...

> David White wrote:
> > And I guess that includes the << functions as well. So, the "hello
world"
> > program in TC++PL is not standard-conforming.
>
> Quite so, and most people do seem to view that as problematic.

And it certainly is. Everyone's first program in C++ might not compile.

> >>It's an instance of type std::ostream; that determines what
> >>can be done on it.
> >
> >
> > I don't know what this means. If the type definition is not present, how
> > does it determine what can be done with it?
>
> What is the "it" there?

The same as yours - std::cout.

> C++ language rules determine what
> operations a type supports, depending on the declarations
> and definitions that are visible. What is not determined
> by the library spec is exactly which those are.

> >>If <ostream> is included, there's plenty
> >>you can do.
> >
> >
> > Like output "Hello world\n" for instance?
>
> Such great achievements, all with only two headers. :-/

Assuming that this problem is going to be addressed at some stage, I don't
believe that any standard-committee will have the stomach to require that
two headers be included to output one string, and the string "Hello
world!\n" in particular. They'll do just about anything to avoid it. I doubt
that it was ever intended that <ostream> be required as well as <iostream>.
I think it's more a case of the standard not reflecting its authors'
intentions than code not conforming to the standard. Therefore, I am of a
mind to join the crowd and simply ignore the standard.

DW


James Dennett

unread,
Dec 19, 2004, 6:30:57 PM12/19/04
to
David White wrote:

> "James Dennett" <jden...@acm.org> wrote in message
> news:exixd.1810$JI.1233@fed1read07...
>
>>David White wrote:
>>
>>>And I guess that includes the << functions as well. So, the "hello
>
> world"
>
>>>program in TC++PL is not standard-conforming.
>>
>>Quite so, and most people do seem to view that as problematic.
>
>
> And it certainly is. Everyone's first program in C++ might not compile.

Suboptimal.

>>>>It's an instance of type std::ostream; that determines what
>>>>can be done on it.
>>>
>>>
>>>I don't know what this means. If the type definition is not present, how
>>>does it determine what can be done with it?
>>
>>What is the "it" there?
>
>
> The same as yours - std::cout.
>

Sorry, I meant your other "it", the "it" that "determines
what can be done with [std::cout]".

>>C++ language rules determine what
>>operations a type supports, depending on the declarations
>>and definitions that are visible. What is not determined
>>by the library spec is exactly which those are.
>
>
>>>>If <ostream> is included, there's plenty
>>>>you can do.
>>>
>>>
>>>Like output "Hello world\n" for instance?
>>
>>Such great achievements, all with only two headers. :-/
>
>
> Assuming that this problem is going to be addressed at some stage, I don't
> believe that any standard-committee will have the stomach to require that
> two headers be included to output one string, and the string "Hello
> world!\n" in particular. They'll do just about anything to avoid it. I doubt
> that it was ever intended that <ostream> be required as well as <iostream>.
> I think it's more a case of the standard not reflecting its authors'
> intentions than code not conforming to the standard. Therefore, I am of a
> mind to join the crowd and simply ignore the standard.

On this one point, that appears to be a reasonably viable option.
More generally, though, it's a fairly bad idea to do so.

-- James

David White

unread,
Dec 19, 2004, 6:48:15 PM12/19/04
to
"James Dennett" <jden...@acm.org> wrote in message
news:iaoxd.2219$JI.451@fed1read07...

> David White wrote:
> >>What is the "it" there?
> >
> >
> > The same as yours - std::cout.
> >
> Sorry, I meant your other "it", the "it" that "determines
> what can be done with [std::cout]".

That one too. I meant that if <ostream> isn't included how does the object
itself determine what can be done with it, but you've answered that
elsewhere.

DW


Alwyn

unread,
Dec 19, 2004, 7:37:21 PM12/19/04
to
On Mon, 20 Dec 2004 09:42:56 +1100, David White wrote:
>
> Assuming that this problem is going to be addressed at some stage, I don't
> believe that any standard-committee will have the stomach to require that
> two headers be included to output one string, and the string "Hello
> world!\n" in particular. They'll do just about anything to avoid it.

Well, it's an embarrassment, a fairly minor one, as these things go.
According to Van Ingen Schenau, it is not considered a defect but may be
addressed in future. I think we can live with that.

The fact is of course that the whole inclusion mechanism is an anachronism
inherited from C. It needs overhauling, a state of affairs that has been
tacitly acknowledged ever since the '.h' suffix was dropped from the
standard headers (which, nota bene, need not be actual files) and template
'export' introduced.

> I doubt
> that it was ever intended that <ostream> be required as well as <iostream>.

Well, we still have that 'non-conforming' example in the standards report,
which, again according to Van Ingen Schenau in this thread, has not been
reported as defective. I perceive here a certain reluctance to face facts.

I hate to say it, but there is every indication that the C++ standard was
rushed out of the door long before it was ready, long before the full
implications of all that had been decided was thought through. It was
widely perceived that a normative document was greatly overdue, and the
standardisers felt themselves under overwhelming pressure to deliver.

To my mind, a wrong turning was taken when it was decided that it was
permissible to invent the language anew rather than codify existing
practice, as is the case with most standardisation efforts. The original
intention was to take the language described in the ARM as a base, but
once the STL was accepted, the ground started to shift rapidly and
dangerously. The result is, frankly, a mess, which it will take many years
to sort out, assuming it can be done at all.

> I think it's more a case of the standard not reflecting its authors'
> intentions than code not conforming to the standard. Therefore, I am of
> a mind to join the crowd and simply ignore the standard.

That is your privilege; after all, it's what everybody else does,
including such eminences as Josuttis, Koenig, Stroustrup etc. etc. I
presume these people are aware that (once more according to Van Ingen
Schenau) conforming code needs to include <memory> in any compilation unit
that makes use of an STL container or 'std::string', yet I have never seen
them follow this precept.


Alwyn

Alwyn

unread,
Dec 19, 2004, 11:13:36 PM12/19/04
to

That is not how I understand it. Consider:

<quote>
27.3 Standard iostream objects [lib.iostream.objects]

Header <iostream> synopsis

namespace std {
extern istream cin;
extern ostream cout;
extern ostream cerr;
extern ostream clog;

extern wistream wcin;
extern wostream wcout;
extern wostream wcerr;
extern wostream wclog;
}

1 The header <iostream> declares objects that associate objects with the
standard C streams provided for by the functions declared in <cstdio>
(_lib.c.files_).
</quote>

At this point, 'istream', 'wostream' etc. are abstract and 'incomplete'
types, about which nothing can be assumed, except that they exist. Any
operations over them, including their member functions, are entirely
unknown.

I suppose you may be relying on annotations like:

<quote>
2 After the object cin is initialized, cin.tie() returns &cout.

ostream cout;
</quote>

to draw your conclusion, but 'cin' and its friends are not initialised
within the header file, where they are merely declared 'extern', but
rather by some process that is invisible to the current compilation unit.

As an illustration, the following code will compile and run on my system:

#include <iosfwd>
#include <istream>
#include <ostream>

namespace std {
extern istream cin;
extern ostream cout;
extern ostream cerr;
extern ostream clog;

extern wistream wcin;
extern wostream wcout;
extern wostream wcerr;
extern wostream wclog;
}

int main()
{
std::ostream *myostream = std::cin.tie();
*myostream << "Hello world!\n";
}

but if I comment out lines 2 and 3, I get the following errors:

iostream.cc: In function `int main()':
iostream.cc:19: error: `tie' undeclared (first use this function)
iostream.cc:19: error: (Each undeclared identifier is reported only once for
each function it appears in.)
iostream.cc:20: error: no match for `std::basic_ostream<char,
std::char_traits<char> >& << const char[14]' operator


Alwyn

bjarne

unread,
Dec 20, 2004, 9:43:42 AM12/20/04
to

David White wrote:

> The examples in the
> standard document and in TC++PL indicate that the who's who of C++
believed
> that <iostream> was sufficient to use the std::cout object for at
least <<
> operations.

> ... Stroustrup and co.,


> like just about everyone else, probably just assumed (or decided)
that
> <iostream> permitted std::cout etc. to be used for any ostream
operation.
> And now people are taking the standard literally and finding that it
doesn't
> actually give that assurance.

I can't speak for everybody, but that's the way it was for me. I was
most surprised to find the traditional "Hello World!" program not
working. I was also somewhat appaled and hope it will become legal
again in the future.
- Bjarne Stroustrup; http://www.research.at.com/~bs

Ben Measures

unread,
Dec 20, 2004, 10:46:21 AM12/20/04
to
Francis Glassborow wrote:
>
> WG21 is giving serious consideration to #include <all> for the benefit
> of programmers who either do not care, or cannot be bothered to
> determine which headers they need.

To me, that sounds like a bad idea, one that will bring the following
code in introductory courses:

> #include <all>
> using namespace std;
>
> int main()
> {
> cout << "Hello, world!" << endl;
> }

The using directive is already common in introductory texts - a
combination of the two could lead to all sorts of confusing name clashes
for new programmers who haven't yet shaken off those (bad) habits. :-/

Having said that, could this be a secret ploy to kill "using namespace
std"? /me raises brow.

--
Ben M.

Chris ( Val )

unread,
Dec 20, 2004, 9:00:13 PM12/20/04
to

"Ben Measures" <saint_abr...@removehotmail.com> wrote in message
news:htCxd.3627$Ar5....@text.news.blueyonder.co.uk...

| Francis Glassborow wrote:
| >
| > WG21 is giving serious consideration to #include <all> for the benefit
| > of programmers who either do not care, or cannot be bothered to
| > determine which headers they need.
|
| To me, that sounds like a bad idea, one that will bring the following
| code in introductory courses:
|
| > #include <all>
| > using namespace std;
| >
| > int main()
| > {
| > cout << "Hello, world!" << endl;
| > }
|
| The using directive is already common in introductory texts - a
| combination of the two could lead to all sorts of confusing name clashes
| for new programmers who haven't yet shaken off those (bad) habits. :-/

[snip]

I'm not sure I can see an automatic increase of name clashes ?

From what I have understood in this thread, the inclusion
of "<all>" is just for standard library headers.

Cheers.
Chris Val


Alwyn

unread,
Dec 21, 2004, 1:39:32 AM12/21/04
to
On Tue, 21 Dec 2004 13:00:13 +1100, Chris ( Val ) wrote:
>
> From what I have understood in this thread, the inclusion
> of "<all>" is just for standard library headers.

I don't know exactly what this '#include <all>' proposal involves, but
that was my impression too.

All the objections have been seen so far have been based on intuition
rather than reasoning or empirical evidence. Intuition, while valuable in
every field of human endeavour, is especially in need of reasoned support
in computing because the machine often gives results that are not
'obvious' at first sight.

My own objection to '#include <all>' would be that in the absence of
precompiled headers or some other accelerating mechanism, it would make
almost every compilation slower, and few people would use it. Long build
times are currently one of the biggest drawbacks to the use of C++ in
large projects.

Incidentally, I have managed to trace the defect report previously cited
by Van Ingen Schenau at:
<http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-closed.html>
It is well worth reading. At the end, it says:

<quote>
Rationale:

The portability problem is real. A program that works correctly on one
implementation might fail on another, because of different header
dependencies. This problem was understood before the standard was
completed, and it was a conscious design choice.

One possible way to deal with this, as a library extension, would be an
<all> header.
</quote>


Alwyn

Francis Glassborow

unread,
Dec 21, 2004, 5:37:41 AM12/21/04
to
In article <32pedbF...@individual.net>, "Chris ( Val )"
<chri...@bigpond.com.au> writes

>From what I have understood in this thread, the inclusion
>of "<all>" is just for standard library headers.

And it is perfectly possible to write your own all.h which does exactly
that (though one or two might be better omitted, cassert springs to
mind).

However if it were a Standard Library header rather than a user written
header file, implementations could treat it quite differently. For
example an implementation could hold a list of all names with extern
linkage, declared anywhere in the Standard Library and look up the
declaration when a user used a name on the list.

The important point is that C++ headers are NOT the same thing as header
files even if they are usually implemented as such.

Francis Glassborow

unread,
Dec 21, 2004, 5:45:03 AM12/21/04
to
In article <pan.2004.12.21....@blueyonder.co.uk>, Alwyn
<al...@blueyonder.co.uk> writes

>My own objection to '#include <all>' would be that in the absence of
>precompiled headers or some other accelerating mechanism, it would make
>almost every compilation slower, and few people would use it. Long build
>times are currently one of the biggest drawbacks to the use of C++ in
>large projects.

Yes, but this is a kind of optimisation problem. For many relatively
small projects, time spent getting determining what headers (note that a
header is necessarily for the C++ Standard Library, and should not be
confused with a header file) need including (particularly when
portability is an issue) is not repaid in better compile times. For
larger projects better granularity may be useful, but I am not so sure
as our hardware has much larger amounts of readily available memory
these days (much of the time cost is in paging data in and out).

In addition an <all> would allow other techniques for implementors (it
might be interesting if some compiler implementor provided it as an
extension coupled with some form of optimised lookup)

Chris ( Val )

unread,
Dec 21, 2004, 7:53:24 AM12/21/04
to

"Alwyn" <al...@blueyonder.co.uk> wrote in message
news:pan.2004.12.21....@blueyonder.co.uk...

| On Tue, 21 Dec 2004 13:00:13 +1100, Chris ( Val ) wrote:
| >
| > From what I have understood in this thread, the inclusion
| > of "<all>" is just for standard library headers.
|
| I don't know exactly what this '#include <all>' proposal involves, but
| that was my impression too.

[snipped fair points]

| Incidentally, I have managed to trace the defect report previously cited
| by Van Ingen Schenau at:
| <http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-closed.html>
| It is well worth reading. At the end, it says:
|
| <quote>
| Rationale:
|
| The portability problem is real. A program that works correctly on one
| implementation might fail on another, because of different header
| dependencies. This problem was understood before the standard was
| completed, and it was a conscious design choice.
|
| One possible way to deal with this, as a library extension, would be an
| <all> header.
| </quote>

Yes, indeed, I too found it to be a good read, thanks.

Cheers.
Chris Val


Chris ( Val )

unread,
Dec 21, 2004, 7:55:53 AM12/21/04
to

"Francis Glassborow" <fra...@robinton.demon.co.uk> wrote in message
news:bqX5kSO1z$xBF...@robinton.demon.co.uk...

| In article <32pedbF...@individual.net>, "Chris ( Val )"
| <chri...@bigpond.com.au> writes
| >From what I have understood in this thread, the inclusion
| >of "<all>" is just for standard library headers.
|
| And it is perfectly possible to write your own all.h which does exactly
| that (though one or two might be better omitted, cassert springs to
| mind).

Right, that's exactly why I questiond it :-)

| However if it were a Standard Library header rather than a user written
| header file, implementations could treat it quite differently. For
| example an implementation could hold a list of all names with extern
| linkage, declared anywhere in the Standard Library and look up the
| declaration when a user used a name on the list.

Oh, good points which I never even considered, thanks.

| The important point is that C++ headers are NOT the same
| thing as header files even if they are usually implemented
| as such.

Agreed.

Cheers.
Chris Val


It is loading more messages.
0 new messages