cojoj cojoj - 18 days ago 5
Swift Question

Calling protocol default implementation from regular method

I'm wondering if it's possible to achieve such a thing.

I have a Playground like this:

protocol Foo {
func testPrint()
}

extension Foo {
func testPrint() {
print("Protocol extension call")
}
}

struct Bar: Foo {
func testPrint() {
// Calling self or super go call default implementation
self.testPrint()
print("Call from struct")
}
}


let sth = Bar()
sth.testPrint()


I can provide a default implementation in
extension
but what if
Bar
needs everything that is in default implementation plus additional things?

It's somehow similar to calling
super.
methods in
class
es to fulfill requirement of implementing every property etc. but I see no possibility to achieve the same with
structs
.

Answer

I don't know if you are still looking for an answer to this, but the way to do it is to remove the function from the protocol definition, cast your object to Foo and then call the method on it:

protocol Foo { 
    // func testPrint() <- comment this out or remove it
}

extension Foo {
    func testPrint() {
        print("Protocol extension call")
    }
}

struct Bar: Foo {
    func testPrint() {
        print("Call from struct")
        (self as Foo).testPrint() // <- cast to Foo and you'll get the  default
                                  //    function defined in the extension
    }
}

Bar().testPrint()

// Output:    "Call from struct"
//            "Protocol extension call"

For some reason it only works if the function isn't declared as part of the protocol, but is defined in an extension to the protocol. Go figure. But it does work.

Comments