[swift-evolution] Proposal: Universal dynamic dispatch for method calls

Kevin Ballard kevin at sb.org
Tue Dec 8 17:26:56 CST 2015


On Tue, Dec 8, 2015, at 03:00 PM, Brent Royal-Gordon wrote:
> > How does this handle the case where the extension was not done in the
> > same module that defined the protocol, and the extension method's name
> > is the same as a method on one of its implementing types (from the same
> > module, or another module that can see the protocol but not the
> > extension)?
> 
> I’m not sure I understand what you’re asking; an annotated code sample might help. But if I *do* understand what you’re saying, that’s what @incoherent on an import is meant to resolve—the case where you import a bunch of modules which don’t individually conflict, but as a group do.

Ah, yeah, looks like your @incoherent does cover this, although I'm not really sure what the benefit of putting @incoherent on an import is. People will just end up putting that there whenever the compiler tells them to, without really understanding why. And when reading the resulting source, it doesn't tell the reader what it's actually trying to resolve, beyond "something to do with type Foo".

> Keep in mind that what I’m proposing here doesn’t actually change Swift’s runtime behavior at all. Note #2—you’re *required* to make protocol extension members `final` unless they’re listed in the protocol declaration. What I’m proposing is merely a series of compile-time statements used to tell swiftc that, yes, I know this is going to happen.

I missed the part about `final` being required.

It seems to me that the only real benefit here is making it so that when you look at a protocol extension you can tell immediately which methods are just default implementations and which ones are actually declaring new extension methods (that can't be overridden). And even that's just saving you from having to look at the protocol declaration to see what methods are in there.

If that visual distinction is useful, I'd rather see this done by using the already-existing `default` keyword as a modifier for methods that are just providing default implementations. And if you try and declare a method in an extension that matches the type signature of a protocol method but doesn't say `default` the compiler would yell at you. This would look something like

protocol Foo {
    func foo() -> String
}

extension Foo {
    // default implementation of Foo.foo()
    default foo() -> String {
        return "foo"
    }
    // new method on all Foos that can't be overridden
    func bar() -> String {
        return "bar"
    }
}

-Kevin Ballard


More information about the swift-evolution mailing list