<html><head><meta http-equiv="Content-Type" content="text/html charset=utf-8"></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space;" class=""><br class=""><div><blockquote type="cite" class=""><div class="">On Aug 22, 2016, at 9:59 PM, Jonathan Hull via swift-evolution &lt;<a href="mailto:swift-evolution@swift.org" class="">swift-evolution@swift.org</a>&gt; wrote:</div><br class="Apple-interchange-newline"><div class=""><div class="">Hi everyone,<br class=""><br class="">We talked about this before when we were discussing mixins, and there seemed to be generally positive feelings towards it as a feature for the future. &nbsp;I am fairly certain this affects the ABI though, so I thought I would bring it up now.<br class=""><br class="">If two protocols have methods/properties with the same name, but different signatures, we need a way to distinguish between them when attempting to conform to both.<br class=""><br class=""><span class="Apple-tab-span" style="white-space:pre">        </span>protocol A {<br class=""><span class="Apple-tab-span" style="white-space:pre">        </span><span class="Apple-tab-span" style="white-space:pre">        </span>var x:Int {get set}<br class=""><span class="Apple-tab-span" style="white-space:pre">        </span>}<br class=""><br class=""><span class="Apple-tab-span" style="white-space:pre">        </span>protocol B {<br class=""><span class="Apple-tab-span" style="white-space:pre">        </span><span class="Apple-tab-span" style="white-space:pre">        </span>var x:Double {get set}<br class=""><span class="Apple-tab-span" style="white-space:pre">        </span>}<br class=""></div></div></blockquote><div><br class=""></div><div>I believe that this can happen, and it is unfortunate that Swift has no mechanism for dealing with it today. However, I agree with Xiaodi that your proposal would be much stronger with real-world examples rather than theoretical ones.</div><br class=""><blockquote type="cite" class=""><div class=""><div class="">One possibility is to allow a struct/class/enum to conform to the protocol while renaming one (or both) of the clashing methods:<br class=""><br class=""><span class="Apple-tab-span" style="white-space:pre">        </span>struct C: A,B {<br class=""><span class="Apple-tab-span" style="white-space:pre">        </span><span class="Apple-tab-span" style="white-space:pre">        </span>var x:Int<br class=""><span class="Apple-tab-span" style="white-space:pre">        </span><span class="Apple-tab-span" style="white-space:pre">        </span>var y:Double implements B.x<br class=""><span class="Apple-tab-span" style="white-space:pre">        </span>}<br class=""><br class="">The conforming method/property would still have to have the same signature, but could have a different name (and parameter labels). &nbsp;It would also allow protocol methods which have identical signatures and semantics, but different names to be implemented using the same method (i.e ‘implements D.z &amp; E.w’).<br class=""><br class="">When something is cast to the protocol (say ‘as B’), then calling the property (e.g. ‘x’) would end up calling the implementation of the renamed property ( ‘y’ in this example) on the conforming type.<br class=""></div></div></blockquote><div><br class=""></div><div>Sure. Calling through the protocol type will get whatever method/property satisfied the protocol requirement. Yes, there are limits here due to protocols with associated types and Self requirements, but I fully expect those to go away at some point with generalized existentials.</div><div><br class=""></div><blockquote type="cite" class=""><div class=""><div class="">I think we would also want a way to retroactively conform using existing properties/methods in an extension declaring conformance. &nbsp;Not sure what the best syntax for that would be. &nbsp;Off the top of my head (though I would love to have something with less cruft):<br class=""><br class=""><span class="Apple-tab-span" style="white-space:pre">        </span>extension D:B {<br class=""><span class="Apple-tab-span" style="white-space:pre">        </span><span class="Apple-tab-span" style="white-space:pre">        </span>@conform(to: B.x, with: D.y)<br class=""><span class="Apple-tab-span" style="white-space:pre">        </span>}<br class=""><br class="">or maybe just:<br class=""><span class="Apple-tab-span" style="white-space:pre">        </span><br class=""><span class="Apple-tab-span" style="white-space:pre">        </span>extension D:B {<br class=""><span class="Apple-tab-span" style="white-space:pre">        </span><span class="Apple-tab-span" style="white-space:pre">        </span>D.y implements B.x<br class=""><span class="Apple-tab-span" style="white-space:pre">        </span>}<br class=""><span class="Apple-tab-span" style="white-space:pre">        </span><br class=""><br class="">All of this is merely to start the discussion, so feel free to propose better syntax or a more elegant solution...<br class=""></div></div></blockquote></div><div class=""><br class=""></div>C# has a much narrower solution that lets you qualify the method declaration (rather than doing a full rename), e.g.,<div class=""><br class=""></div><div class=""><span class="Apple-tab-span" style="white-space:pre">        </span>struct C : A {</div><div class=""><span class="Apple-tab-span" style="white-space:pre">        </span>&nbsp; var x: Int</div><div class=""><span class="Apple-tab-span" style="white-space:pre">        </span>&nbsp; var y: Double</div><div class=""><span class="Apple-tab-span" style="white-space:pre">        </span>}</div><div class=""><br class=""></div><div class=""><span class="Apple-tab-span" style="white-space:pre">        </span>extension C : B {</div><div class=""><span class="Apple-tab-span" style="white-space:pre">        </span>&nbsp; var B.x: Double {</div><div class=""><span class="Apple-tab-span" style="white-space:pre">        </span>&nbsp; &nbsp; get { return y }</div><div class=""><span class="Apple-tab-span" style="white-space:pre">        </span>&nbsp; &nbsp; set { y = newValue }</div><div class=""><span class="Apple-tab-span" style="white-space:pre">        </span>&nbsp; }</div><div class=""><span class="Apple-tab-span" style="white-space:pre">        </span>}</div><div class=""><div class=""><br class=""></div><div class="">They have some examples at:</div><div class=""><br class=""><div class=""><span class="Apple-tab-span" style="white-space:pre">        </span><a href="https://msdn.microsoft.com/en-us/library/aa288461(v=vs.71).aspx" class="">https://msdn.microsoft.com/en-us/library/aa288461(v=vs.71).aspx</a></div><div class=""><br class=""></div><div class="">One would have to figure out what the name-lookup rules are, of course, but this might allow us to solve the problem without introducing a generalized renaming mechanism.</div><div class=""><br class=""></div><div class=""><span class="Apple-tab-span" style="white-space:pre">        </span>- Doug</div><div class=""><br class=""></div></div></div></body></html>