<div dir="ltr">I recently had the misfortune of deleting what turned out to be a necessary function, because it was an optional requirement of a protocol and wasn&#39;t being called by any code in the project, so I would sympathise with this.<div><br></div><div>On the other hand I&#39;ve also written protocols composed entirely of functions that an established type already has, so I can retroactively have the type conform. (For example, there&#39;s no &#39;ArithmeticOperation&#39; protocol which Int and Double both conform to, even though they both have a `+ (lhs:Self, rhs:Self) -&gt; Self` operator, so you have to roll your own... unless that should be a proposal itself.) It would be impossible to require a function to use your &#39;implements&#39; keyword to conform to a protocol in an importing module.</div></div><div class="gmail_extra"><br><div class="gmail_quote">On Fri, Mar 18, 2016 at 11:58 PM, Victor Gao via swift-evolution <span dir="ltr">&lt;<a href="mailto:swift-evolution@swift.org" target="_blank">swift-evolution@swift.org</a>&gt;</span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><div style="word-wrap:break-word"><div><font face="HelveticaNeue" style="font-size:14px">Hello everybody. Please excuse this proposal’s poor formatting. I am very new to swift-evolution and don’t yet know how to do a formatted proposal. :)</font></div><div><font face="HelveticaNeue" style="font-size:14px"><br></font></div><div><br></div><div><font size="5" face="HelveticaNeue"><b>Proposal</b></font></div><div><font face="HelveticaNeue" style="font-size:14px"><br></font></div><div><font face="HelveticaNeue" style="font-size:14px">I am proposing to add an </font><font style="font-size:14px" face="Courier">implement</font><font face="HelveticaNeue" style="font-size:14px"> keyword to go with protocol method implementations like the </font><font style="font-size:14px" face="Courier">override</font><font face="HelveticaNeue" style="font-size:14px"> keyword.</font></div><div><font face="HelveticaNeue" style="font-size:14px"><br></font></div><div><br></div><div><font size="5" face="HelveticaNeue"><b>Motivation</b></font></div><div><span style="font-size:14px"><font face="HelveticaNeue"><br></font></span></div><div><span style="font-size:14px"><font face="HelveticaNeue">When writing an implementation for a protocol method, there is no indication that the method is an implementation of a protocol method. Unless it is a well-known protocol like </font><font face="Courier">UITableViewDataSource</font><font face="HelveticaNeue">, there is simply no way to know if the method is provided by a protocol or the enclosing class. Right now, the only way to guess if a method is protocol-provided is if it follows the pattern of </font><font face="Courier">someObjectOrView(_: requestSomething:) </font><font face="HelveticaNeue">or </font><font face="Courier">someObjectOrView(_: somethingDidHappen:)</font><font face="HelveticaNeue">. But since non-Cocoa protocol methods may not follow that pattern, they will not be so easy to guess. </font><span style="font-family:HelveticaNeue">Here’s an example illustrating the problem:</span></span></div><div><font face="HelveticaNeue" style="font-size:14px"><br></font></div><div><font style="font-size:14px" face="Courier"><font color="#b92d5d">func</font> recordInDatabase(database: <font color="#008cb4">TJDatabase</font>, atIndexPath indexPath: <font color="#7b219f">NSIndexPath</font>) -&gt; <font color="#008cb4">TJRecord</font> {</font></div><div><font style="font-size:14px" face="Courier">    <font color="#669c35">//…</font></font></div><div><font style="font-size:14px" face="Courier">}</font></div><div><font style="font-size:14px" face="Courier"><br></font></div><div><font face="HelveticaNeue"><span style="font-size:14px">Is this a protocol method implementation, or simply a method declaration? Well, it <i>looks</i> like a protocol method implementation, but how can one be sure? There is no way to definitely know unless you are familiar with it or you found its declaration after searching in the whole project, worse in huge projects. The method above just seems too “ordinary” to be a protocol method implementation. Even worse, some developer might come around and even rename that method, and there would be an error, then he has to fish around for the protocol method he’s missing. Assuming that he finally found it (if the protocol is small enough), he might even implement it <i>again</i> with the <i>same</i> code as the renamed method. We can see the problem here.</span></font></div><div><font face="HelveticaNeue"><span style="font-size:14px"><br></span></font></div><div><font face="HelveticaNeue"><span style="font-size:14px">Or, let’s think about this: how would it feel if there is no </span></font><font face="Courier" style="font-size:14px">override</font><font face="HelveticaNeue"><span style="font-size:14px">  keyword? How would one know if a method is an override or not? We can see how this relates to the confusion with protocol method implementations.</span></font></div><div><font face="HelveticaNeue"><span style="font-size:14px"><br></span></font></div><div><br></div><div><font face="HelveticaNeue" size="5"><b>Proposed solution</b></font></div><div><span style="font-size:14px"><font face="HelveticaNeue"><br></font></span></div><div><span style="font-size:14px"><font face="HelveticaNeue">The proposed solution is to add an </font><font face="Courier">implement</font><font face="HelveticaNeue"> keyword, which improves the code above to this:</font></span></div><div><span style="font-size:14px"><font face="HelveticaNeue"><br></font></span></div><div><span style="font-size:14px"><font face="Courier"><font color="#b92d5d">implement func</font> recordInDatabase(database: <font color="#008cb4">TJDatabase</font>, atIndexPath indexPath: <font color="#7b219f">NSIndexPath</font>) -&gt; </font><span style="font-family:Courier"><font color="#008cb4">TJRecord</font> {</span></span></div><div><font face="Courier" style="font-size:14px">    <font color="#669c35">//…</font></font></div><div><font face="Courier" style="font-size:14px">}</font></div><div><font face="Courier" style="font-size:14px"><br></font></div><div><font face="HelveticaNeue"><span style="font-size:14px">Now it is very clear that we are implementing a protocol method rather than declaring a method. The code is much clearer, and it doesn’t hurt the readability either.</span></font></div><div><font face="HelveticaNeue"><span style="font-size:14px"><br></span></font></div><div><br></div><div><b style="font-family:HelveticaNeue"><font size="5">Detailed design</font></b></div><div><br></div><div><span style="font-size:14px"><font face="HelveticaNeue">When overriding implemented protocol methods from a superclass, the </font><font face="Courier">override</font><font face="HelveticaNeue"> keyword is still used:</font></span></div><div><span style="font-size:14px"><font face="HelveticaNeue"><br></font></span></div><div><div><span style="font-size:14px"><font face="Courier"><font color="#b92d5d">override func</font> recordInDatabase(database: <font color="#008cb4">TJDatabase</font>, atIndexPath indexPath: <font color="#7b219f">NSIndexPath</font>) -&gt; </font><span style="font-family:Courier"><font color="#008cb4">TJRecord</font> {</span></span></div><div><font face="Courier" style="font-size:14px">    <font color="#b92d5d">return</font> <font color="#b92d5d">super</font>.<font color="#00a3d7">recordInDatabase</font>(database, atIndexPath: indexPath)</font></div><div><font face="Courier" style="font-size:14px">}</font></div></div><div><font face="HelveticaNeue"><span style="font-size:14px"><br></span></font></div><div><font face="HelveticaNeue" size="5"><b>Impact on existing code</b></font></div><div><br></div><div><span style="font-size:14px">Existing code would be changed to include the <font face="Courier">implement</font> keyword in appropriate places. This could be handled via the Swift latest syntax converter in Xcode. </span></div><div><br></div><div><br></div><div><br></div><div><br></div></div><br>_______________________________________________<br>
swift-evolution mailing list<br>
<a href="mailto:swift-evolution@swift.org">swift-evolution@swift.org</a><br>
<a href="https://lists.swift.org/mailman/listinfo/swift-evolution" rel="noreferrer" target="_blank">https://lists.swift.org/mailman/listinfo/swift-evolution</a><br>
<br></blockquote></div><br></div>