Hacker News new | ask | show | jobs
by wool_gather 2873 days ago
It seems this is what you get when you decide dynamic dispatch is a demon that must be cast out. :/ It's a good example of Swift's at-times-infuriating insistence on chasing performance at the expense of developer ergonomics. That said, I'm sure it will be mediated eventually (although probably with more compiler annotations).
2 comments

The problem here is that Swift is sort of this hybrid between two disparate worldviews, the old Objective-C world where inheritance is cool and dispatch is dynamic and the new world where inheritance is not even permitted and traits are used to provide dynamic dispatch. It's trying to be everything to everyone. This is one of those crossover points where the seams don't meet. If this was all dynamic, it would be fine because the messages would be dispatched properly. If this was all new world, you wouldn't even be allowed to subclass, would refer to your trait explicitly, and again, everything would work fine.

This is a fundamental structural issue with the language, philosophically, and will definitely cost programmer productivity. I'd argue this isn't a problem so much as behaves correctly due to insufficient planning.

It's not that they're taking a position on dynamic dispatch, it's that they're trying to take both positions, likely in support of Objective-C compatibility.

IMO dynamic dispatch has caused way more programmer productivity issues than anything else - you write code the compiler can't validate because you explicitly chose not to give it the information it needs to do it's job. It can't tell you your code is right. Nothing really can. The new world is a better place, Go and Rust have it right, inheritance is dead.

While inheritance is OK, and useful in programming-by-difference scenarios, Objective-C style polymorphism has always de-emphasized inheritance.

Dynamic dispatch is central to both the most productive and largest-scale software systems/environments in the world. If you think the compiler can tell you everything, you're in for a world of hurt, and if you think you can statically type-check the world: good luck.

Again, inheritance is useful, though overused in static languages that only allow polymorphism together with inheritance.

Objective-C deemphasizes formal inheritance. Class clusters and informal protocols generally substitute for some of the benefits that inheritance can give.
I guess fundamentally, this is the question I have about this situation: would you ever, in real code, want dispatch to go straight back to the default implementation when you have in hand a value with a custom implementation?

I may be having a failure of imagination; but I certainly haven't ever seen a case where I'd want that.

I’d imagine the issue lies in Swift classes utilizing only static dispatch. The protocol conformance creates a witness table populated by the methods of the class in question, but as Swift classes have no vtables except in ObjC compatability mode (right?) there’s no way to pass down the invocation from the protocol witness to a specific subclass as the method can not be resolved at runtime. This is the difference between the dynamic dispatch via witness table and the explicit static dispatch to the subclass when type information is available.

Thus it comes down to dynamic dispatch always (or at least for anything that has a protocol conformance at all) vs surprising behavior here.

I do agree with you, however.

Classes do get dynamic dispatch at least for methods/properties that can be overridden (i.e., `open`). I believe the value must also still have a reference to its class's method impls -- otherwise what happens when you cast it `if let noReallyLazyGreeter = lazyGreeter as? LazyGreeter {`? Not certain about these details, though.
This is far too far, and a lot of it is wrong
If you could elaborate on what is wrong with it, that would be helpful, compared to just dismissing it.
Yeah I’d love to have a conversation about your thoughts here!
> infuriating insistence on chasing performance at the expense of developer ergonomics

It would be slightly less infuriating had that chase actually delivered, but it dramatically has not.