When I'm done explaining how it's you, actually, who is the one who doesn't understand basic programming language theory and terms, and how you keep embarrassing yourself with hilariously false objections, you will probably need to apologize to me for this embarrassing and childish temper tantrum of yours.

>First one call matches exactly one return. Then the same call matches a bunch of returns. Which is it?

There is usually a very basic distinction in Programming between 2 things : the runtime and the compile time. At compile time, the expression 5/0 is a perfectly valid integer expression, it returns an integer that can be used in all subsequent calculations. At runtime, it's a hardware trap, and the entire program will probably abort because of it. Integer or hardware trap? Which one is it? Both.

At compile time, a call site has a finite (and obvious) set of returns it's associated with, usually a relatively small set. At runtime, however, a single return out of this set ends up returning control to the call site. So a call site is associated at compile time with a small set of very obvious returns, and at runtime with a single return drawn from this set. Anyone who doesn't understand this probably hasn't programmed enough time to have a worthwhile opinion.

>Then, a catch catches innumerable throws?

Yes indeed. Every single type-compatible exception that can possibly be thrown on the call stack beneath a catch is catchable by it, this is, contrary to what you imagine, an exponential set, and I do really mean exponential, yes:

If 2 function are called in a try{} block, and each of those 2 function then calls 2 function, and each of those last 2 function then calls another 2 function, then the set of possible throws catchable by your original catch is all throws in the 8 functions. Catch candidate sets are exponential in the number of function calls in the try{} block they catch. Unlike an ordinary call site that can resume control from a very small set of known locations, a catch can resume control from an huge and intractable set of jumps.

>it is only ever caught exactly once

Actually, it's at most once.

>You don't get to count that as a flaw

I do and I did. Exceptions are not some family members of yours to be this defensive and upset because I criticized them. It's okay, people can hate things that you (unhealthily) love, learn to deal with it. It gets better.

>Exceptions are not, in fact, dynamically typed.

This was a subtle point in my comment, so of course you didn't understand it and went on to angry ranting as usual. Here's a more detailed explanation of what I meant by that:

When you call a function foo() and assign the result it returns to an int, the compiler of any decent language will ensure that every single return in foo returns an int. Alternatively and equivalently, if you declare foo() as an int, every single variable that holds the result of foo is an int, else compiler complains.

This doesn't happen in exceptions.

In exceptions, you can throw a FileNotFoundException, in a function that only catches NetworkTimeoutException. The compiler won't complain. You can later call that function in a function that only catches DictKeyNotFoundException, and the compiler won't complain about the lack of catch for FileNotFoundException. You can keep doing this till the very end, forever in fact, always putting incompatible catches around the function that throws, and the compiler will never once complain.

It's in this sense that throwing exceptions is like a dynamically typed returns, it throws an object, i.e returns data, but the compiler never bothers to check for a matching reception of this object at the calling code, like it does for ordinary returns.

Java tried to solve this with its Checked Exceptions, but it also introduced Unchecked Exceptions that anybody can use and thus greatly reduced the benefit and use of Checked Exceptions.

>Look up "exponentially"

Try thinking about something for 5 minutes before you hit the keyboard. It will payoff greatly.

>Any catch block that doesn't lexically match that type is skipped over.

Look up "lexically". It does not mean what you seem to imagine.

A "lexical" thing, in programming language theory, is that which can be inferred from program text alone without running it. Catches don't work lexically because they respect subtyping (i.e inheritance). And with subtyping comes runtime polymorphism.

Specifically, if

- Cat and Dog are both subtypes of Animal, an abstract class\interface, and

- I'm catching a Cat,

Then if I throw an Animal exception, the question "Will my catch, catch that exception?" can't be resolved lexically, or from program text alone without running it. The catch will catch if the object pointed to by the Animal reference I threw is a Cat, it won't catch if the object pointed to by the Animal reference I threw is a Dog. Seriously, go run it and tell me if I'm wrong.