Why is not more FreeBSD software written in C++?
Benjamin Lutz
benlutz at datacomm.ch
Sun Apr 23 00:03:12 UTC 2006
On Saturday 22 April 2006 17:11, Dan Strick wrote:
> On Friday 21 Apr 2006 09:20, Don Dugger wrote:
> > The example above is not exactly a realworld example. Even if you stick
> > to plain C, a repeated putchar(' ') is 1-2 orders of magnitude slower
> > than aggregating those characters and write()'ing them every few dozen
> > chars.
>
> This might seem obvious, but is it really true? I wrote a program that
> tries it both ways with the output redirected to /dev/null and discovered
> that filling a 24 character buffer and doing a write() takes about 11 times
> as much cpu time as 24 putchar()s. Perhaps a buffer larger than a "few
> dozen chars" would be useful. There must be a moral here somewhere. :-)
Yes, it is really true. Since I don't know what your test is, I've created my
own.
test_putchar.c:
----
#include <stdlib.h>
#include <stdio.h>
int main(int argc, char** argv) {
int i, j;
for (i = 0; i < 50000; i++) {
for (j = 0; j < 60; j++) {
putchar('.');
}
putchar('\n');
}
return 0;
}
----
test_write.c:
----
#include <stdlib.h>
#include <unistd.h>
int main(int argc, char** argv) {
char buf[61];
int i, j;
for (i = 0; i < 50000; i++) {
for (j = 0; j < 60; j++) {
buf[j] = '.';
}
buf[60] = '\n';
write(STDOUT_FILENO, buf, 61);
}
return 0;
}
----
And for completeness' sake, two corresponding C++ iostream variants:
test_iostream.cpp:
----
#include <iostream>
using namespace std;
int main(int argc, char** argv) {
for (int i = 0; i < 50000; i++) {
for (int j = 0; j < 60; j++) {
cout << '.';
}
cout << '\n';
}
return 0;
}
----
test_string.cpp
----
#include <iostream>
using namespace std;
int main(int argc, char** argv) {
for (int i = 0; i < 50000; i++) {
for (int j = 0; j < 60; j++) {
cout << '.';
}
cout << '\n';
}
return 0;
}
----
All files are compiled with gcc/g++ and the -O2 option. I'm running them on a
Mac Mini under Linux.
And the results are (I've run that command several times and picked a line
that shows an average run time):
$ time ./test_putchar > /dev/null
./test_putchar > /dev/null 0.39s user 0.00s system 97% cpu 0.397 total
$ time ./test_write > /dev/null
./test_write > /dev/null 0.02s user 0.01s system 82% cpu 0.029 total
$ time ./test_iostream > /dev/null
./test_iostream > /dev/null 0.94s user 0.00s system 99% cpu 0.950 total
$ time ./test_string > /dev/null
./test_string > /dev/null 0.21s user 0.00s system 97% cpu 0.213 total
That quite clearly shows that my prediction that using putchar is "1-2 orders
of magnitude slower" is accurate. It also shows the points you and others
have made that iostream is slower than C's I/O mechanisms.
If we take the two most sensible variants, test_write and test_iostream, and
have them write into a file, we get these numbers:
$ time ./test_write > foo
./test_write > foo 0.01s user 0.16s system 95% cpu 0.180 total
$ time ./test_string > foo
./test_string > foo 0.20s user 0.02s system 98% cpu 0.223 total
Which is a small enough difference to be irrelevant. The large I/O performance
advantage of the write(2) variant over the C++ string variant vanishes as
soon as the code actually does something remotely useful.
> I am not claiming that strings and iostreams are bad. I am observing
> that some reasonable programs that use these facilities will run very
> slowly and I am suggesting that it is not always obvious which programs
> these are.
You mentioned a pretty printer. I'm not convinced that the performance
drawbacks you saw were inherent in iostream. Rather it seems that the comfort
of C++'s strings and streams led the programmer to program in a less
performance-conscious way.
> I am also expressing disappointment because I want the
> decision to use any feature of C++ or its standard library to be a
> no-brainer.
Personally, I don't hesitate to use features of C++. As for the STL... there
are nice alternatives that are sometimes available. When writing Qt programs,
I'll use Qt's data structures only, not the STL ones, since imo Qt's data
structure classes are more comfortable to use.
Cheers
Benjamin
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 191 bytes
Desc: not available
Url : http://lists.freebsd.org/pipermail/freebsd-chat/attachments/20060423/8eedbb45/attachment.pgp
More information about the freebsd-chat
mailing list