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

Patrick Smith pgwsmith at gmail.com
Fri May 20 20:49:02 CDT 2016


Straight Any<class> sounds good to me. Otherwise keep it at AnyObject. Renaming it to AnyClass does not seem right, especially as there already is one present in Swift 2 with the different meaning.


> On 21 May 2016, at 10:40 AM, Brent Royal-Gordon via swift-evolution <swift-evolution at swift.org> wrote:
> 
>> The Any-class requirement could replace the current `AnyObject` protocol with a typealias like this: `typealias AnyObject = Any<class>`
>> 
>> Assume Swift would introduce Any-struct and Any-enum requirement one day. How would one name a typealias for these, where `AnyClass` means `AnyObject.Type`?
>> 
>> I suggest we drop the current `AnyClass` and rename `AnyObject` to `AnyClass`. If one would need the old `AnyClass` behavior it will become `AnyClass.Type`.
> 
> I propose that we deprecate `AnyObject` in favor of `Any<class>`. No typealias, just directly using `Any<>`. We would also deprecate `AnyClass` in favor of `Any<class>.Type`. (Presumably we would do this by providing `AnyObject` and `AnyClass` typealiases in Swift 3, but marking them as deprecated.)
> 
> I like this approach because it exposes people to `Any<>` and more quickly gets them to see how it's connected to a protocol declaration's conformance list. They might then guess that `Any<>` has other capabilities from that list, like the ability to handle multiple protocols.
> 
>> In the future we could have typealiases like this, which are more clear:
>> 
>> `typealias AnyClass = Any<class>`
>> `typealias AnyStruct = Any<struct>`
>> `typealias AnyEnum = Any<enum>`
> 
> Even in the long term, I don't see any good reason to support `Any<struct>` vs. `Any<enum>`. There is no semantic distinction* between a struct and an enum; you can always implement something enum-y using a struct with a mode field, or something struct-y using an enum with associated values. `Bool`, for instance, was once an enum and was changed to a struct for implementation reasons; this change made no difference to how it was used.
> 
> Now, there *is* a semantic distinction between struct/enum and class—one is a value type, the other is a reference type. To support that distinction, it might make sense to support an `Any<value>` or `Any<!class>` syntax. Again, I would prefer to use the raw `Any<>` syntax, though, not a typealias.
> 
> (I've read the arguments about pure vs. non-pure value type conformances and I'm not convinced. It is always possible to nominally "conform" to a protocol in a way that actually undermines its guarantees; for example, you could implement `RangeReplaceableCollection.remove(at:)` as a no-op. The compiler cannot reject all invalid conformances; it can only reject ones which it can trivially show are invalid, because for instance they do not even attempt to provide a required method. Similarly, the compiler may not be able to prove you are providing value semantics, but it *can* reject conformances of reference types to a protocol requiring value semantics, since those cannot possibly be valid conformances.
> 
> Incidentally, I am not convinced that it *ever* makes sense to have a mutating protocol which does not specify either value or reference semantics. The only intentional Stdlib examples I'm aware of are `IteratorProtocol` and `OutputStream`, and I think both of those should be reference-only.
> 
> (On the other hand, it might make sense to be able to mark a struct or enum as "this is actually a reference type". For instance, if you import libc, UnsafeMutablePointer<FILE> is essentially a reference type. But on the gripping hand, you *could*, and perhaps should, just wrap it in a class, either through importer magic or a manually-created type. That would permit you to conform it to reference-typed mutating protocols.))
> 
> 
> 
> * There *are* some distinctions, particularly in pattern matching, but protocols can't model them anyway. Incidentally, it is not possible to satisfy static property/method requirements with cases, but it probably should be:
> 
>    protocol OptionalProtocol { 
>        associatedtype W
>        static var none: Self { get } 
>        static func some(value: W) -> Self 
>    } 
>    extension Optional: OptionalProtocol {
>        typealias W = Wrapped
>    }
> 
> 
> -- 
> Brent Royal-Gordon
> Architechies
> 
> _______________________________________________
> swift-evolution mailing list
> swift-evolution at swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution



More information about the swift-evolution mailing list