HN Books @HNBooksMonth

The best books of Hacker News.

Hacker News Comments on
Design and Evolution of C++, The

Bjarne Stroustrup · 8 HN comments
HN Books has aggregated all Hacker News stories and comments that mention "Design and Evolution of C++, The" by Bjarne Stroustrup.
View on Amazon [↗]
HN Books may receive an affiliate commission when you make purchases on sites after clicking through links on this page.
Amazon Summary
This book focuses on the principles, processes and decisions made during the development of the C++ programming language. As the inventor of the language, Stroustrup presents his insight into the decisions which resulted in the features of C++ - the praised, the controversial and even some of the rejected ones. By writing this book the author presents his object-oriented programming philosophy to the interested programming community. His vehicle is the C++ language but his focus is on real object-oriented programming language development for the working programmer rather than as a abstract approach to the OOP paradigm.
HN Books Rankings

Hacker News Stories and Comments

All the comments and stories posted to Hacker News that reference this book.
Here’s one that’s a hit or miss depending on your interests: The Design And Evolution of C++ by Bjarne Stroustrup himself.

https://www.amazon.com/Design-Evolution-C-Bjarne-Stroustrup/...

Even if you dislike C++, or like me, came to loathe it, I highly recommend the book he published in the same year, The Design and Evolution of C++ (https://www.amazon.com/Design-Evolution-C-Bjarne-Stroustrup/...). It's very educational about you go about making a successful language in an existing ecosystem, and even after swearing off the language I don't regret one bit the time I spent reading the book.
ArkyBeagle
The sort of puppy-dog C++ style on Arduinos - a sort of pedomorphic variation on "'C' with classes", chock full of singletons and the inability of constructors to operate unless they're called in A Certain Place - pretty much works.

What's less attractive is Dogmatic Bikeshedding C++ OO Fundamentalism.

TickleSteve
its actually the full gcc compiler on arduino.... not that they advertise that.
ArkyBeagle
They were pretty upfront about it being gcc/g++ - the "Arduino" part are the built-in things like Serial.
mlvljr
Behave yourself! How dare...
santaclaus
> What's less attractive is Dogmatic Bikeshedding C++ OO Fundamentalism.

Is that a thing? I always saw more of that in the Java world than C++ -- Java's standard library is rife with the singleton factory decorator monstrosities that have come to be associated with OO, C++ and the standard library have always felt more generic-programy. Now egregious use of obscure template meta programming tricks because of perceived (vs measured) performance gains, I've seen some horrors there...

pjmlp
When the design patterns book was written it was all about Smalltalk and C++.

I guess you missed the boat on CORBA, COM and DCOM, fun days...

J2EE architects were mostly former C++ architects that moved into Java land.

Also UWP APIs are actually the second coming of COM as .NET was originally supposed to be.

lallysingh
It's a solid book, but I wish there was something newer. It's 20 years old now!
npiazza83
If America were a year it would be out for all of December.
krylon
I agree. I only spent very little time with C++, but that book was both highly interesting and very entertaining to read. Highly recommended!
profeta
how can you loathe C++ without caming to loathe it? i mean, everyone is bound to hate it, but you have to try it first to be sure...
hga
I think it's flaws, only somewhat addressed in recent revisions, are better known now than they were in the mid-'90s when I learned and started using it, plus the industry wide ... obsession? with OO and especially class based OO has subsided. So someone with good taste who reads and trusts what he reads of these details could, yeah, probably not legitimately loathe it, but at least decide without using it that it wasn't for him.

I changed the initial use of loathe in this context to dislike, thanks for pointing that out.

clappski
... I like it ...
ArkyBeagle
Just don't assume loathing is linear...
armitron
How can you loathe Krokodil without coming to loathe it? You have to try it first to be sure...
mlvljr
Russky drug addicts on HN? :V
byuu
After seeing P0145R3 on C++17 refinements to expression order guarantees (and many things like that before it) ... I think I've finally started to actively dislike C++ now as well, after nearly 20 years of using it daily.

They had a golden opportunity to fix it, but even with C++17 and the expression "a(b(), c());", it is still left indeterminate whether b() or c() will be invoked first. Even between calls in the same program! So what if they have side effects? It might be a picosecond faster if the compiler can run c() first to push its argument onto the stack first!

I'm all for the power for C and C++ to optimize to such efficient code, and not consume many resources. But we're a long ways from the PDP-11 days and processor frequencies measured in KHz, and compiler developers are living in some alternate reality where the only thing that matters are benchmarks, and they'll happily undermine the stability and security of our software by doing things like erasing that call to memset() that cleared your private key from memory; or remove that conditional expression entirely because it detected the possibility of an integer overflow, so that means it can do whatever it wants! ... even though the world has been twos-complement for decades now.

Given the very real security concerns and exploits we keep seeing in code ... I don't believe that using languages full of undefined/unspecified behavior is the way to build stable and reliable systems.

Nobody can keep track of the hundreds of UB cases in C/C++. We all do it, and then suddenly a new GCC comes out with a new benchmark optimization, and now our programs are misbehaving.

I'm willing to pay a 5-10% penalty, and give up compatibility with the Motorola 68000 platform, to get well-defined and predictable behavior. Maybe you keep C/C++ for that gaming OS, or that Wall Street trading system. But on my server? I can spare the CPU cycles.

And yet, everything is built on C/C++. Your OS? That Python interpreter? Your web browser's Javascript engine? The .NET runtime? All C/C++ under the hood. We're building on quicksand; when we need a solid foundation.

vvanders
> I'm willing to pay a 5-10% penalty, and give up compatibility with the Motorola 68000 platform, to get well-defined and predictable behavior. Maybe you keep C/C++ for that gaming OS, or that Wall Street trading system. But on my server? I can spare the CPU cycles.

Come over to the land of Rust, where you can keep your high performance memory semantics and safety :).

Seriously, life-long C++ dev here. Been writing C++ for almost 20 years now and I don't feel like there's anything I could do in C++ that I can't in Rust(both performance and functionality-wise).

None
None
pjmlp
I dabble with it every time a new release comes out, but I feel it still lacks many features relevant to me and our customers, ability to easily interoperate with COM like .NET languages, C++/CX, Delphi, C++ Builder do, is one of them.
yongjik
I'm not a big fan of UB either, but keeping the order of argument evaluation indeterminate seems very sensible to me.

Imagine you have a function like f(int, double). If argument evaluation order is fixed, you can no longer exchange the order of arguments: for all you know, someone might be depending on the first argument being evaluated first!

byuu
If there's really a performance advantage to argument reordering then you can do it whenever there are less than two arguments that may have side effects. Safe instances would be:

* constants

* regular variables that aren't using the cast constructor for implicit conversion

* member functions marked const

* constexpr functions

You would only need to actually evaluate function calls that may change global state, or that perform in-place assignment (eg f(x += 1, x += 2)).

I will take the performance impact of doing something 'stupid' like calling f(a(), b()) instead of splitting the expression up into three lines any day over potentially introducing a security vulnerability that I don't even know about and that the compiler doesn't warn me about any day of the week.

Performance is not the be-all end-all of the world. We should not make critical applications insecure in order to get our apps to be 0.0001% faster.

> If argument evaluation order is fixed, you can no longer exchange the order of arguments: for all you know, someone might be depending on the first argument being evaluated first!

... I don't understand how moving from arbitrary argument evaluation ordering to fixed argument evaluation ordering can possibly turn any valid code existing today into bad code. Quite the opposite, it has the potential to fix a lot of code. Anything that relied on the arguments being evaluated backward (I don't even know of a compiler that does that ... yet) would have been technically broken per the previous language specs anyway. So I don't know what point you are trying to make here, sorry.

yongjik
My scenario is:

* There's a function f(int, double), called in ~100 places, written by many different people.

* For some reason I decide to change it to f(double, int). Consistency, or preparing for some other refactoring, whatever.

* I have to track down ~100 occurrences of f and exchange arguments. Time-consuming but no big deal.

* If any code was dependent upon compiler silently evaluating the arguments in a particular way, then the code was broken, and reasonably competent coders don't write too much broken code. (Moreover, such a dependency is 99% likely to be broken by random changes in codes or compiler options, so chances are that I wouldn't encounter too many such bugs.)

In your world, it is just about impossible. If I want to go ahead, I could either change every occurrence into:

    int arg1 = ...;
    double arg2 = ...;
    f(arg2, arg1);
...or pore through every line calling f to see if it's safe.

C++ already has a reputation of being a difficult language to refactor, and your proposal will make it about impossible.

ScottBurson
I've spent over three decades using languages that guarantee left-to-right evaluation order (Common Lisp and Java), and I have not found this to be a problem in practice.
byuu
Ah, I understand what you're saying now. I guess we'll have to agree to disagree, then.

I am much more interested in predictability in my code than I am about reordering arguments in mature codebases.

Lots of languages guarantee expression ordering to follow precedence and associativity rules, and I've never heard anyone say that it was a problem to refactor their code as a result.

Whereas I am 100% certain that there are lots of codebases where this is a ticking timebomb with developers unintentionally relying on the order their compiler decides to evaluate expressions in. And it will blow up when, not if, the GCC devs find some micro-optimization and decide to reverse things on them. And that's not just a problem for them, it's a problem for everyone who relies on their code.

netheril96
The standards body move very slowly. More practical approach is to push compilers to add more options to define undefined behavior so that we have safety with the minor cost of performance. We already have -fwrapv, -ftrapv and -fno-strict-aliasing. We could ask for more and a general -fsafe flag.
byuu
I definitely use -fwrapv already. Unfortunately, there is no -fhonor-precedence-associativity switch in GCC or Clang. And I would need it in both to support all the systems I target.

But even moreso, yes!! I would love if we had a -fsafe directive that turned undefined behavior from "do whatever is fastest" into "do whatever is most expected." I would seriously start paying $100 a year to use such a compiler -- not even joking a little.

Unfortunately, as I've said, the compiler devs seem to have lost touch completely with the developers using the language and love playing these nasty games with UB. So I'm not sure how we can go about getting them to implement such a flag. And I just don't have the bandwidth to fork and maintain GCC or Clang to do it myself =(

mastax
UBSan is not quite the same thing, but it's quite good.

http://clang.llvm.org/docs/UndefinedBehaviorSanitizer.html

pjmlp
> We already have -fwrapv, -ftrapv and -fno-strict-aliasing.

You have it in specific compilers, not in the standard.

Not everyone is able to go installing clang and gcc on their work platform, when there are so many compilers to choose from.

https://en.wikipedia.org/wiki/List_of_compilers#C.2B.2B_comp...

None
None
wildmusings
>They had a golden opportunity to fix it, but even with C++17 and the expression "a(b(), c());", it is still left indeterminate whether b() or c() will be invoked first.

If the order of b() and c() matter, then they shouldn't be in the same statement. That is an abomination. What you little you gain in terseness, you more than make up for in future headaches.

byuu
That is not an abomination. Turning this:

    int val = a(b(c(), d()), e(f(), g()));
Into this:

    auto _1 = c();
    auto _2 = d();
    auto _3 = b(_1, _2);
    auto _4 = f();
    auto _5 = g();
    auto _6 = e(_4, _5);
    int val = a(_6);
Is the abomination.

Expecting every programmer to know that a(b(), c()); may call b() first or may call c() first is an abomination. Having a programmer's app work fine on most PCs, and then suddenly having a security vulnerability that takes down my server because a compiler dev decided to exploit this on my system in order to save two clock ticks on a 4GHz CPU is an abomination.

Here's a more tangible use case:

    template<typename... P> void print(P&&...);
    print("The value of: ", binaryObject.getNextToken(), " is ", binaryObject.getNextToken(), "\n");
Looks sensible, until you find out that the compiler decides to switch the parameter ordering and you get the value before the name.

And it's not just me: the point of that PR was because people were doing exactly that with cout << next() << next(); and they clarified the rules so that was permissible. They just ignored function calls, so we are stuck using uglier than sin operator overloading of left-shift for our print statements, if we want predictable argument evaluation. Apparently the 'performance penalty' there is reasonable, so why not for function calls? So now we have to remember that in C++17, cout's ordering is left-to-right, yet print()'s ordering is effectively completely random.

wildmusings
>int val = a(b(c(), d()), e(f(), g()));

I'll stick by my original assertion. If the order of those invocations matter, then they shouldn't be on the same line, regardless of whether the actual behavior is well-defined or not. Just one example of what can go wrong: parameter reordering is often done automatically by tools, or manually by someone who is not intimately familiar with the code, such as six-months-in-the-future you.

Six operations with side effects--especially conflicting side-effects--belong on six lines. Six lines on your screen is not worth the days potentially spent searching for a future bug.

msorvig
But this is not particularly good imperative style. You want that to be line-based when expressions have side effects. ("one thing after another"):

  auto key = binaryObject.getNextToken();
  auto value = binaryObject.getNextToken();
  print("The value of: ", key, " is ", value, "\n");
Of course if you are calling pure functions you can use nested expressions. And then the order of evaluation does not matter.
byuu
> You want that to be line-based when expressions have side effects.

No, I really don't. I don't want three lines instead of one line of code. And I don't want two named variables leaking into my scope. (I could encapsulate the block with {} here, but if print returned a value that I wanted to capture, then I couldn't do that.)

willtim
I believe the issue is that C++ does not track what are, and are not pure functions, so the ordering optimisation is, in general, unsafe.
Apr 23, 2015 · pjmlp on C# 7 Work List of Features
Yes.

Most of the C++ warts are caused by the need to be copy-paste compatible with C, expectations of C developers being lured into this new language and be a drop-in compatible replacement for C tooling.

"The Design and Evolution of C++", http://www.amazon.com/The-Design-Evolution-Bjarne-Stroustrup...

aeonsky
If the entire C++ codebase I worked with was mostly C, my job would be so much easier. I think the 2000+ page C++ manual proves my point.
That could be really good.

Although I've come to loathe the language, his 1994 book on the topic is fantastically good and highly recommended: http://www.amazon.com/The-Design-Evolution-Bjarne-Stroustrup...

Another good read are The Annotated C++ Reference Manual[1] and The Design and Evolution of C++[1].

They help understand all design compromises that were done to keep compatibility with C, which is was part of what brought C++ into the mainstream, but also the main cause of many of its warts.

[1] http://www.amazon.com/The-Annotated-C-Reference-Manual/dp/02...

[2] http://www.amazon.com/The-Design-Evolution-Bjarne-Stroustrup...

signa11
> Another good read are The Annotated C++ Reference Manual[1] and The Design and Evolution of C++[1].

Annotated C++ Reference Manual as well as D&E is severely dated. Quite a while back there was some talk of stroustrup co-authoring a revision of the reference-manual with andrew-koenig, but it never came to fruition...

pjmlp
That is true, but the point here is to learn how C++ got designed in first place, you can't update that.
While not a complete history, the following book, 'Design and Evolution of C++', does go into some history of other languages that influenced C++:

http://www.amazon.com/The-Design-Evolution-Bjarne-Stroustrup...

If you happen to be in bay area, visiting the 'Computer History Museum' is a good start too:

http://www.computerhistory.org/

Dec 26, 2010 · sharednothing on A Year Of Scala
Please point out the "shortcomings" of Java. It has done quite well and provably "scales" from programming in the small to enterprise level. Even the required detour of multi-core resulted in the industry's gold standard of memory models: JMM.

"Much smaller language specification" is a red herring. The issue is (practical) comprehension.

"C was a well designed language that was later added onto haphazardly and you ended up with C++."

http://www.amazon.com/Design-Evolution-C-Bjarne-Stroustrup/d...

I've read that book. (Have you?) Nothing "haphazard" about C++.

runT1ME
Shortcomings: Generics. Lack of closures. Please tell me how those are not shortcomings.

>Even the required detour of multi-core resulted in the industry's gold standard of memory models: JMM.

Which has absolutely zero to do with java the language. Did you forget what we were talking about in your second sentence?

sharednothing
We were discussing the "mistakes" made by the Java design team. JMM is one of their products. It is relevant to mention this fact as it supports the claim that the responsible parties have generally been also quite brilliant folks.
code_duck
I consider verbosity and lack of closures to be shortcomings of Java. Apparently, so did the author of the article here.
sharednothing
Its perfectly fine to note that Java can be verbose and that it does not fully support closures. It is perfectly fine to consider these "shortcomings".

However, in context of OP's comment above, the strong suggestion made was that shorcoming == poorly designed.

And that is a completely wrong assessment of Java and its designers. It is an exceptionally well thought out system and language. Again, the proof is in the pudding. Google and Oracle are not fighting over scala ...

somnium
They're not fighting over Java, they're fighting over the JVM. Java isn't worth fighting over.
sharednothing
The fact remains that the JVM was designed for Java and mirrors its semantics.

The "shortcoming" of Java is due to none other than the JVM:

http://java.sun.com/developer/technicalArticles/DynTypeLang/...

sharednothing
The downvotes on my comments are quite pathetic. Take the time to review HN guidelines. I recognize that hitting that down arrow takes far less effort to formulate a coherent response, but hey, you are supposed to be a Geek. Use that gray matter, little brother.
None
None
jimbokun
If issues such as verbosity and whether or not to have closures are not part of the language design process, then what is?
sharednothing
That is a non sequitur.

A language designer must make choices. 2 choices have been identified as "shortcomings" (in the sense of this thread). Empirical evidence suggests that they indeed picked a very productive sweet spot.

As an aside, the current disfavor of "crowds" for Java is all together too familiar to the past fervor of "crowds" for Java. You may wish to reflect on that.

jimbokun
"Empirical evidence suggests that they indeed picked a very productive sweet spot."

You seem to be arguing that popularity and quality are synonymous. I do not think that is a very useful way to evaluate programming languages.

Do you have actual data showing productivity gains for using Java over Scala or other languages that run on the JVM? How about Java and non-JVM languages? Even anecdotal evidence? You are advocating for empirical evidence, but are not providing much in this discussion that I can see.

sharednothing
"You seem to be arguing that popularity and quality are synonymous. I do not think that is a very useful way to evaluate programming languages."

No. And yes, of course. (Java is not exactly "popular" these days.)

"Do you have actual data showing productivity gains for using Java over Scala or other languages that run on the JVM?"

Do you have actual data from a study that shows such studies are worth their virtual ink? Cite it, please. Lets pretend we have an actual market economy in this country: How many businesses have shot themselves in the foot with Java? How many have bet the farm (IBM, Oracle, even Google has hedged on this tech) on Java? Are they all idiots who do not appreciate the grave "shortcomings" of Java and its impact on the "productivity" of their workers ants? Are you kidding me?

"You are advocating for empirical evidence, but are not providing much in this discussion that I can see."

One needs to point out the overwhelming presence of Java in OSS? Well, consider it pointed out. Pretty darn good showing for a language with such serious "shortcomings".

Anecdotal? Have been programming since 16. That was 30 years ago. Have done/seen enough to have a reasonably informed opinion regarding languages. Everyone of them has its set of issues. Java included. But it is actually one of the most productive languages I have worked with to date.

runT1ME
>but it is actually one of the most productive languages I have worked with to date.

Because of the language design, or because of the libraries and the jvm (GC, the fact that it's bytecode, etc)?

Do you think Scala would make you less productive?

Feb 12, 2010 · hga on Learning C++ in 2010
It's very old and I have no idea how accurate it still is, but I found Inside the C++ Object Model by Stanley Lippman (http://www.amazon.com/Inside-Object-Model-Stanley-Lippman/dp...) to be tremendously useful in the mid-'90s for understanding what was going on under the hood.

Stroustrup's The Design and Evolution of C++ (http://www.amazon.com/Design-Evolution-C-Bjarne-Stroustrup/d...) is very good for explaining the "why" of C++, especially the stranger parts.

One other note, echoing some of the others: everyone picks out a subset of C++ and programs in that, and smart companies make that formal. You might see if your problem domain matches one of the available good ones, like Google's (well, I've heard that it's good).

HN Books is an independent project and is not operated by Y Combinator or Amazon.com.
~ yaj@
;laksdfhjdhksalkfj more things
yahnd.com ~ Privacy Policy ~
Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.