SE-0309: Unlock existential types for all protocols

OK.

Many Swift users don't know the difference between func f<T: P>(parameter: T) and func f(parameter: P) — I too was one of those people at some point. The confusion stems from the lack of an indication that parameter is bound to the existential type of P; any P should hopefully change that.

Do you mean that users could perhaps conflate () -> any Usable and <^T: Usable>() -> T — the latter syntax is borrowed from here?

To me, the any-some distinction, between existentials and generics respectively, makes sense. Namely, some Hashable indicates that a value of some (a singular, specific) Hashable-conforming type will be returned. On the contrary, any Hashable indicates that any (an unspecified type, not always the same) Hashable-conforming type can be returned (and wrapped in the existential), meaning we can do this: (Bool.random() ? "" ? 0) as any Hashable but can't do the same with some.

That was metaphorical, but unfortunate wording on our part, nonetheless.

I disagree. Syntactic friction can encourage certain styles and discourage others; for example, requiring that existentials be written out as ThisIsAnExistentialOfProtocol<Hashable> would result in many preferring <T: Hashable> T where possible, choosing the path of least resistance.

Documentation can help but it's not enough.

To be clear, we don't propose altering the existential syntax; let a: any Hashable will be invalid.

Swift tends to avoid abbreviations.

I think these would be poor name choices.

The only benefit I see to Object<Protocol> is the fact that it's a concrete type; however, that would be undermined if we enabled func f(_: Optional<some Hashable>). Nevertheless, I don't think naming should be based on implementation details (existentials don't have reference semantics — mutating one doesn't change another), not to mention that many users would think that Object is referring solely to classes. (If we use this syntax, then Array which isn't backed by value types, should be called ArrayObject.)

2 Likes