[swift-evolution] [Pitch] Rename `AnyObject` to `AnyClass` and drop current `AnyClass`

Dave Abrahams dabrahams at apple.com
Sun May 22 21:40:52 CDT 2016


on Sun May 22 2016, Brent Royal-Gordon <swift-evolution at swift.org> wrote:

>> I haven't had the
>> chance to consider all the implications yet, but—at least until someone
>> can demonstrate that we really custom == for classes—we should be open
>> to the idea as we consider the value semantics story.
>
> I've been lurking and skimming the discussion around this so far, but
> I'll speak up at this point. I really do think making `==` always be
> an identity check for class types is not a realistic option.
>
> What you're proposing is essentially what Objective-C does. When Swift
> was introduced, the ability to use operators like `==` to mean
> *logical* equality instead of *referential* equality was touted as a
> major advantage. And it *is* a major advantage for readability—`text1
> == text2` (where text1 and text2 are, say, NSMutableString or
> NSAttributedString) is much nicer than `text1.isEqual(text2)`. 

Yes, but:

1. The equality operator is supposed to mean substitutability, and the
   the fact that identity is significant for mutable class types means
   `==` instances are not substitutable for one another.

2. IIUC these things should not be reference types in Swift, and pretty
   soon they won't be.

> We would be giving up a significant feature of the language for a
> vision of purity that most programmers don't (think they) care about.

Not for a “vision of purity;” for coherence and simplicity.  If Swift
was about addressing only things programmers *think* they care about, we
wouldn't have value semantic arrays or strings.

> Now, one thing you *could* do is allow overloading of `==` and instead
> take `===` for this purpose. `===` is already an identity check on
> reference types and unavailable on value types; for value types, it
> could be defined as always equivalent to `==`. This would leave `==`
> open to user definition on class types, while exposing your value
> equality operation as `===`.

I think that would continue to break generic programming.  There are
already a few generic components in the standard library that won't work
as expected with reference types, and these were written by people aware
of the issue!  I don't think this is a practical programming model for
most people.

We'd have to tell them, “it doesn't matter that your algorithm seems to
work just fine with `==` when you tested it with `Int`s; you have to use
`===` or it will break in subtle ways when used with reference types.
And when you *do* use `===`, remember that you're only getting reference
equality, so the equality semantics you normally expect for mutable
reference types doesn't apply.”  It's just not a tenable system.

> Either way, though, if `Hashable` is always identity-based on class
> types, that will cause bridging issues. 
> NSDictionary and Dictionary (or NSSet and Set) will no longer agree on
> which objects are distinct and which are not. Converting from the
> Swift type to the Foundation type and back again may lose elements. If
> we broaden `===` to all instances, `Hashable` will probably still need
> to be tied to `==`, not `===`.

If all these reference types bridge to values in Swift, I don't think we
have a problem.

> It's unfortunate that those darned users are always getting in the way
> of our elegant designs. :^)

Smiley aside, I don't agree with your implication that I'm prioritizing
purity over user experience.  This is *all about* the user experience.

-- 
-Dave



More information about the swift-evolution mailing list