[swift-evolution] [Review] SE-0091: Improving operator requirements in protocols

Brent Royal-Gordon brent at architechies.com
Wed May 25 03:15:58 CDT 2016

>> As Brent pointed out in his reply, without multiple dispatch, you don't really benefit from privileging the lhs argument, and in fact you can end up in situations where the behavior is surprising if you don't implement both orders. For example, in your (NSString, NSURL) example, each class would have to be extended to explicitly support comparison with the other in order to support commutativity if equality was an instance method. I'm not sure that's any better for those particular types than just having the operators global in the first place.
> I assume you’d still have to implement it with NSObject as the “other” type, like you do in Objective-C. You’d just return false in that case.

It is rather unfortunate, though, that your `(Self, Self)` operator essentially becomes `(Self, NSObject)` once `NSObject` conforms. I mean, Swift will at least *tell* you this is happening and force you to write an `other as? Self` test, but the way the type of the right-hand side gets pinned down while the left-hand side stays unspecified is just strange.

(Incidentally, I think rather than returning `false` here, you probably ought to say:

	guard let other = other as? Self else {
		return super == other

Would you be able to use `super` in that way? You probably ought to, if we're planning to use left-side dispatch.)

Meanwhile, a multi dispatch solution would send two otherwise unrelated types to `NSObject`'s implementation, which would `===` the two instances, discover they were not identical, and return `nil`. More specific implementations would not even have to think about this case; the method dispatch would just do it for them. I don't know if that solution is feasible, but if it is, it seems clearly correct—it simply gives you the right behavior every single time with no hand-wringing about type mismatches.

(On the other hand, if we *do* use left-side dispatch, we might be able to solve the `isEqual` interop problems complained about upthread: if `==` is implicitly given an `@objc(isEqual:)` attribute, and `isEqual` definitions or calls are fix-it-ed to `==`, the problem essentially solves itself.)

Brent Royal-Gordon

More information about the swift-evolution mailing list