Live data from Hacker News

Orthodox C++ (2016)

bkaradzic.github.io

191–200 of 238 posts

Re: Orthodox C++ (2016)

#191

Earlier quoted context omitted.

> Throwing lets you handle the new situation without changing the API at all. I do not disagree. https://xkcd.com/1172/ If you add exceptions to a library that didn’t previously use them then I almost definitely have to update my code. The fact that it compiles and runs but will behave in undesirable ways makes it even worse, not better! > or if you really must not throw from the function, I’m aware. But if your libr…

> If you add exceptions to a library that didn’t previously use them then I almost definitely have to update my code. No, that's the whole point. You let them bubble up to the top of the event loop and you report the error to the user. As a user, anything else leads to shitty software where the programmer tries to outsmart the world around them (and fails, obviously, leading to worse end-user experience than just adm…

What user? I work on systems where there might not be a keyboard or a mouse or a display and where the use of there is one doesn’t care that the “flooblutz was out of turving.” The only thing stack unwinding gets me is it forces me to restart my program from the beginning.

Re: Orthodox C++ (2016)

#192

Earlier quoted context omitted.

Funny this predates even the original paper first introducing the attention mechanism underpinning modern LLM.

What are you talking about? Are you claiming ~two weeks ago predates LLMs or am I misinterpreting what you're trying to say?

[deleted]

Re: Orthodox C++ (2016)

#193

Earlier quoted context omitted.

You're using "contract" in a different sense than I did. When I said "contract" I was referring to the required state of the program when the function is called and the guaranteed state of the program when the function returns. By definition an exception cannot be part of the contract in this sense, because a call that throws does not return. This narrower sense of contract is critical, because the entire point of ex…

Okay, but if I may offer a suggestion: in the future, I would probably phrase what you said differently. I think it caused you trouble here not just with me but with other readers. Instead of "when the function cannot fulfill its contract", I would talk about "when returning would not fulfill a function's contract." There are actually two reasons for this, not one: - It violates standard terminology. The notion of a…

>How exactly have you seen people use exceptions to "report errors" that is not for the purpose of indicating that "a contract cannot be fulfilled"?

Reporting normal errors to the caller, as opposed to exceptional errors. The distinction between normal errors and exceptional errors is kind of nebulous, but it boils down to normal errors being those that the immediate caller would be interested in, and everything else is exceptional.

For example, you have a file system class that abstracts away different underlying hardware interfaces to present to the client code a virtual file system. Not only would it be impractical for the open() function to include as part of its interface every possible error condition of all the possible backends, it would be of no help to the caller. If you're manipulating an AbstractFileSystem class just to open a path and read data, what could you possibly do with a connection reset error, or with a file system structure corruption error? Do you see what I mean? They're errors happening at different levels of abstraction. Exceptions are meant to be used to communicate error conditions when your call stack looks like

(low abstraction) ---> (high abstraction) ---> (high abstraction) ---> (low abstraction)

often with a module boundary between high abstraction stack frames. You use them to pass errors directly between frames at the same level of abstraction, that are not in direct communication.

So to answer your question, exceptions are misused when they communicate relevant errors within the same level of abstraction, such as an open() function throwing a FileNotFoundException.

Re: Orthodox C++ (2016)

#194
post #83

Earlier quoted context omitted.

and even std::map, std::unordered_map, even std::vector (!) suck It's really hard to take your comment serious because of generalization like this. Maybe they're not usable for your particular usecase but that doesn't mean they suck. Just like there's a 'million' ways that C++ sucks in your book, there's a reason there's millions of lines of code out there where these containers are valid usecases and hence work with…

They're not useable for anything serious, i.e. high throughput, low frequency, massively concurrent work. In other words, most of the things for which you shouldn't better have chosen a different language in the first place. They're also unusable by the way because of ergonomic and software architecture factors, such as bad modularity, terrible compile times, unreadable error messages, unreadable symbol names... Yes…

If you haven't been thinking deeply about memory management and concurrency, you won't be able to understand, no offense meant

I do think about that, when needed. My point is that these containers can be 'good enough' in places where it doesn't really matter, not that they're always the go-to thing. E.g. I really don't see any issue using a map as part of a configuration type of object which gets read from args or json and which only gets used once at application start.

Re: Orthodox C++ (2016)

#195
post #57

Earlier quoted context omitted.

A lot of us are too busy solving problems. Learning about the latest language features, which we often won't be able to use anyway due to the trouble of moving a large dev environment to a newer standard, feels like academic masturbation. C++ folks are very much into their language, and can't seem to understand that most folks don't want to dedicate significant amounts of mental resources purely to language details.

Moving to new C++ is a non event, change the compiler / flags and done. Using the new features requires some learning but not a big deal since you can figure out what you need from a summary and learn what is useful for your problem. The problems of the code I'm writing far exceeds the complexity of the language. Your complaint about complexity fall flat to me, unless you are working on a trivial program you need to…

It's really not. For us, changing compiler versions has noticeable effects throughout our codebase. I'm glad you don't have to deal with that though.

Re: Orthodox C++ (2016)

#197

Earlier quoted context omitted.

> Throwing lets you handle the new situation without changing the API at all. I do not disagree. https://xkcd.com/1172/ If you add exceptions to a library that didn’t previously use them then I almost definitely have to update my code. The fact that it compiles and runs but will behave in undesirable ways makes it even worse, not better! > or if you really must not throw from the function, I’m aware. But if your libr…

>The fact that it compiles and runs but will behave in undesirable ways makes it even worse, not better! * Exceptions * Unstable API * Incorrect behavior Pick your poison. I know what I prefer. >But if your library that offers foo adds exceptions now I need to think about it at every single callsite You really don't. Like I said, it's kind of the whole point of exceptions. >In my 20+ years of professional C++ develop…

> You really don't. Like I said, it's kind of the whole point of exceptions.

No, this is actually just wrong. With exceptions you “don’t have to think about” the exception getting caught by some higher level catch.

But you do have to think about it in the sense that every single line in your code could unwind. Which makes ensuring you remain in a valid state more difficult.

One of the issues with exceptions isn’t the throw. It’s what do you do after you catch.

> That a tool can be misused doesn't delegitimize the tool.

I’m always open to the possibility that if something I’ve seen has been bad 100 times then on the 101st it might be good. But at some point you really just have to call a spade a spade.

Re: Orthodox C++ (2016)

#198

Earlier quoted context omitted.

>The fact that it compiles and runs but will behave in undesirable ways makes it even worse, not better! * Exceptions * Unstable API * Incorrect behavior Pick your poison. I know what I prefer. >But if your library that offers foo adds exceptions now I need to think about it at every single callsite You really don't. Like I said, it's kind of the whole point of exceptions. >In my 20+ years of professional C++ develop…

> You really don't. Like I said, it's kind of the whole point of exceptions. No, this is actually just wrong. With exceptions you “don’t have to think about” the exception getting caught by some higher level catch. But you do have to think about it in the sense that every single line in your code could unwind. Which makes ensuring you remain in a valid state more difficult. One of the issues with exceptions isn’t the…

>But you do have to think about it in the sense that every single line in your code could unwind.

No, this is actually just wrong. There is code that can throw, and there is code that cannot possibly throw. The way you write exception-safe code is by not holding manually-managed resources (e.g. raw pointers that own heap allocations, or file descriptors that must be close()d, or anything else that needs cleanup code that has not been put in a destructor) during sections that may throw. In other words, use RAII to manage your resources, regardless of whether exceptions may be thrown.

Re: Orthodox C++ (2016)

#199

Earlier quoted context omitted.

> You really don't. Like I said, it's kind of the whole point of exceptions. No, this is actually just wrong. With exceptions you “don’t have to think about” the exception getting caught by some higher level catch. But you do have to think about it in the sense that every single line in your code could unwind. Which makes ensuring you remain in a valid state more difficult. One of the issues with exceptions isn’t the…

>But you do have to think about it in the sense that every single line in your code could unwind. No, this is actually just wrong. There is code that can throw, and there is code that cannot possibly throw. The way you write exception-safe code is by not holding manually-managed resources (e.g. raw pointers that own heap allocations, or file descriptors that must be close()d, or anything else that needs cleanup code…

Program state is significantly more complex than just needing some RAII resources to cleanup via destructors.

> during sections that may throw

Yeah one of the problems with exceptions is it’s impossible to know what “may throw” other than “well I guess literally anything so everything”. It is very irritating.

At the end of the day exceptions are just a little syntactic sugar. Or perhaps syntactic bitters.

It is notable that systems languages designed after C++ all chose to not include exceptions. Go, Zig, Swift, Odin, Jai.

Rust panics are kinda sorta exceptions in that they unwind. But their intended use case is for irrecoverable errors. And of course you can set panic=abort.

C++ exceptions are very rarely treated as so serious module level irrecoverability.

Re: Orthodox C++ (2016)

#200

Earlier quoted context omitted.

> If you add exceptions to a library that didn’t previously use them then I almost definitely have to update my code. No, that's the whole point. You let them bubble up to the top of the event loop and you report the error to the user. As a user, anything else leads to shitty software where the programmer tries to outsmart the world around them (and fails, obviously, leading to worse end-user experience than just adm…

What user? I work on systems where there might not be a keyboard or a mouse or a display and where the use of there is one doesn’t care that the “flooblutz was out of turving.” The only thing stack unwinding gets me is it forces me to restart my program from the beginning.

^^^ truth speaker
Post reply on HN