[swift-evolution-announce] [Review] SE-0089: Replace protocol<P1, P2> syntax with Any<P1, P2>


(J.E. Schotsman) #1

Maybe we should adopt a Swift specific definition of existential, like

"An existential type is a type derived from Any with constraints of the kinds listed below:"
...

For example, the 5 kinds of constraint proposed by Austin Zheng.
Not very academic, but might save some discussion.

That would include the existing Protocol as type (no associated type or Self requirements).
Also Any<ClassName> which equals the class (which hides type information through automatic upcasting of subclass instances).

A narrower definition might require protocols to be involved somehow and the resulting type must be new (not equivalent to a class or struct or enum).


(Adrian Zubarev) #2

There is great feedback going on here. I'd like to consider a few things here:

What if we name the whole thing `Existential<>` to sort out all confusion? This would allow `typealias Any = Existential<>`.
Should `protocol A: Any<class>` replace `protocol A: class`? Or at least deprecate it.
Do we need `typealias AnyClass = Any<class>` or do we want to use any class requirement existential directly? If second, we will need to allow direct existential usage on protocols (right now we only can use typealiases as a worksround).

···

--
Adrian Zubarev
Sent with Airmail

Am 25. Mai 2016 um 23:26:25, Jan E. Schotsman via swift-evolution (swift-evolution@swift.org(mailto:swift-evolution@swift.org)) schrieb:

Maybe we should adopt a Swift specific definition of existential, like

"An existential type is a type derived from Any with constraints of
the kinds listed below:"
...
...
...

For example, the 5 kinds of constraint proposed by Austin Zheng.
Not very academic, but might save some discussion.

That would include the existing Protocol as type (no associated type
or Self requirements).
Also Any<ClassName> which equals the class (which hides type
information through automatic upcasting of subclass instances).

A narrower definition might require protocols to be involved somehow
and the resulting type must be new (not equivalent to a class or
struct or enum).

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


(Dave Abrahams) #3

There is great feedback going on here. I'd like to consider a few things here:

* What if we name the whole thing `Existential<>` to sort out all
confusion?

Some of us believe that “existential” is way too theoretical a word to
force into the official lexicon of Swift. I think “Any<...>” is much
more conceptually accessible.

···

on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org> wrote:

  This would allow `typealias Any = Existential<>`. * Should
`protocol A: Any<class>` replace `protocol A: class`? Or at least
deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
want to use any class requirement existential directly? If second, we
will need to allow direct existential usage on protocols (right now we
only can use typealiases as a worksround).

--
Dave


(Adrian Zubarev) #4

I’m not against Any<…> or something, I just wanted to throw this in the room because I’ve seen someone being confused about what Any<…> might mean. The generic manifesto has a nice wordplay that explains the true meaning: “Any type that conforms to … (all constraints) … .”

But someone might still think that this type awaits any type from within the angle brackets (something like oneOf<A, B>).

···

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:15:19, Dave Abrahams via swift-evolution (swift-evolution@swift.org) schrieb:

on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org> wrote:

There is great feedback going on here. I'd like to consider a few things here:

* What if we name the whole thing `Existential<>` to sort out all
confusion?

Some of us believe that “existential” is way too theoretical a word to
force into the official lexicon of Swift. I think “Any<...>” is much
more conceptually accessible.

This would allow `typealias Any = Existential<>`. * Should
`protocol A: Any<class>` replace `protocol A: class`? Or at least
deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
want to use any class requirement existential directly? If second, we
will need to allow direct existential usage on protocols (right now we
only can use typealiases as a worksround).

--
Dave

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


(L Mihalkovic) #5

How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.

···

On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org> wrote:

on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org> wrote:

There is great feedback going on here. I'd like to consider a few things here:

* What if we name the whole thing `Existential<>` to sort out all
confusion?

Some of us believe that “existential” is way too theoretical a word to
force into the official lexicon of Swift. I think “Any<...>” is much
more conceptually accessible.

This would allow `typealias Any = Existential<>`. * Should
`protocol A: Any<class>` replace `protocol A: class`? Or at least
deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
want to use any class requirement existential directly? If second, we
will need to allow direct existential usage on protocols (right now we
only can use typealiases as a worksround).

--
Dave

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


(L Mihalkovic) #6

Inventing all these oneOf<> AllOf<> feel like an incomplete algebra that only exist because of a fixation on cramming everything inside the Any<> box.

What are they? How will they be described in Swift programming manuals? Pseudo protocols? Protocols? Then what will their .Type be?

I'm sorry, I cannot see where this is all going.

···

On May 26, 2016, at 7:23 PM, Adrian Zubarev via swift-evolution <swift-evolution@swift.org> wrote:

I’m not against Any<…> or something, I just wanted to throw this in the room because I’ve seen someone being confused about what Any<…> might mean. The generic manifesto has a nice wordplay that explains the true meaning: “Any type that conforms to … (all constraints) … .”

But someone might still think that this type awaits any type from within the angle brackets (something like oneOf<A, B>).

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:15:19, Dave Abrahams via swift-evolution (swift-evolution@swift.org) schrieb:

on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org> wrote:

> There is great feedback going on here. I'd like to consider a few things here:
>
> * What if we name the whole thing `Existential<>` to sort out all
> confusion?

Some of us believe that “existential” is way too theoretical a word to
force into the official lexicon of Swift. I think “Any<...>” is much
more conceptually accessible.

>
> This would allow `typealias Any = Existential<>`. * Should
> `protocol A: Any<class>` replace `protocol A: class`? Or at least
> deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
> want to use any class requirement existential directly? If second, we
> will need to allow direct existential usage on protocols (right now we
> only can use typealiases as a worksround).

--
Dave

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


(Vladimir) #7

Don't think {} is better here, as they also have "established meaning in Swift today".

How about just Type(P1 & P2 | P3) - as IMO we can think of such construction as "creation" of new type and `P1 & P2 | P3` could be treated as parameters to initializer.

func f(t: Type(P1 & P2 | P3)) {..}

···

On 26.05.2016 20:32, L. Mihalkovic via swift-evolution wrote:

How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.

On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org> wrote:

on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org> wrote:

There is great feedback going on here. I'd like to consider a few things here:

* What if we name the whole thing `Existential<>` to sort out all
confusion?

Some of us believe that “existential” is way too theoretical a word to
force into the official lexicon of Swift. I think “Any<...>” is much
more conceptually accessible.

This would allow `typealias Any = Existential<>`. * Should
`protocol A: Any<class>` replace `protocol A: class`? Or at least
deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
want to use any class requirement existential directly? If second, we
will need to allow direct existential usage on protocols (right now we
only can use typealiases as a worksround).

--
Dave

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


(Adrian Zubarev) #8

Something like type<…> was considered at the very start of the whole discussion (in this thread), but it does not solve the meaning of an existential type and also might lead to even more confusion.

···

From my perspective I wouldn’t use parentheses here because it looks more like an init without any label Type.init(…) or Type(…). I could live with Any[…] but this doesn’t look shiny and Swifty to me. Thats only my personal view. :wink:

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:48:04, Vladimir.S via swift-evolution (swift-evolution@swift.org) schrieb:

Don't think {} is better here, as they also have "established meaning in
Swift today".

How about just Type(P1 & P2 | P3) - as IMO we can think of such
construction as "creation" of new type and `P1 & P2 | P3` could be treated
as parameters to initializer.

func f(t: Type(P1 & P2 | P3)) {..}

On 26.05.2016 20:32, L. Mihalkovic via swift-evolution wrote:

How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.

On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org> wrote:

on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org> wrote:

There is great feedback going on here. I'd like to consider a few things here:

* What if we name the whole thing `Existential<>` to sort out all
confusion?

Some of us believe that “existential” is way too theoretical a word to
force into the official lexicon of Swift. I think “Any<...>” is much
more conceptually accessible.

This would allow `typealias Any = Existential<>`. * Should
`protocol A: Any<class>` replace `protocol A: class`? Or at least
deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
want to use any class requirement existential directly? If second, we
will need to allow direct existential usage on protocols (right now we
only can use typealiases as a worksround).

--
Dave

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


(Thorsten Seitz) #9

We could just write

let x: P & Q
instead of
let x: Any<P, Q>

let x: Collection where .Element: P
instead of
let x: Any<Collection where .Element: P>

let x: P & Q where P.T == Q.T
instead of
let x: Any<P, Q where P.T == Q.T>

let x: P & Q & R
instead of
let x: Any<P, Q, R>

let x: Collection
instead of
let x: Any<Collection>

This would avoid the confusion of Any<T1, T2> being something completely different than a generic type (i.e. order of T1, T2 does not matter whereas for generic types it is essential).

-Thorsten

···

Am 26.05.2016 um 20:11 schrieb Adrian Zubarev via swift-evolution <swift-evolution@swift.org>:

Something like type<…> was considered at the very start of the whole discussion (in this thread <https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160502/016523.html>), but it does not solve the meaning of an existential type and also might lead to even more confusion.

From my perspective I wouldn’t use parentheses here because it looks more like an init without any label Type.init(…) or Type(…). I could live with Any[…] but this doesn’t look shiny and Swifty to me. Thats only my personal view. :wink:

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:48:04, Vladimir.S via swift-evolution (swift-evolution@swift.org <mailto:swift-evolution@swift.org>) schrieb:

Don't think {} is better here, as they also have "established meaning in
Swift today".

How about just Type(P1 & P2 | P3) - as IMO we can think of such
construction as "creation" of new type and `P1 & P2 | P3` could be treated
as parameters to initializer.

func f(t: Type(P1 & P2 | P3)) {..}

On 26.05.2016 20:32, L. Mihalkovic via swift-evolution wrote:
> How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.
>
>> On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
>>
>>
>>> on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
>>>
>>> There is great feedback going on here. I'd like to consider a few things here:
>>>
>>> * What if we name the whole thing `Existential<>` to sort out all
>>> confusion?
>>
>> Some of us believe that “existential” is way too theoretical a word to
>> force into the official lexicon of Swift. I think “Any<...>” is much
>> more conceptually accessible.
>>
>>>
>>> This would allow `typealias Any = Existential<>`. * Should
>>> `protocol A: Any<class>` replace `protocol A: class`? Or at least
>>> deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
>>> want to use any class requirement existential directly? If second, we
>>> will need to allow direct existential usage on protocols (right now we
>>> only can use typealiases as a worksround).
>>
>> --
>> Dave
>>
>> _______________________________________________
>> swift-evolution mailing list
>> swift-evolution@swift.org <mailto:swift-evolution@swift.org>
>> https://lists.swift.org/mailman/listinfo/swift-evolution
> _______________________________________________
> swift-evolution mailing list
> swift-evolution@swift.org <mailto:swift-evolution@swift.org>
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution


(L Mihalkovic) #10

It seem to me we are debating the how of a what that has not been defined. The root question behind all these alternatives seems to be to decide if the existential-ness should be carried by a 'container' that is then refined internally, or derived from the presence of the free-floating refinements. This is the question that splits the possible syntaxes into these 2 groups:

Any<> Any[]
Type<> Type<>
Existential<>

and the (these are all straw man representations that should not limit the thinking)

P & Q
@P and @Q
is P , Q
P & Q typed

If the answer is to use a 'container' then the next question is to see its relationship to the other existing containers: is it the result of a transformation, is it a superset, or a super type; it is obviously lossy, but not entirely if the solution follows in some of Brent's past suggestion to make some existential types instantiate-able (which opens a very similar problem to what java faced for several years when trying to identify a universal collection literal syntax).
That will narrow down the field of possible matches... until one syntax emerges as conveying the meaning that is reflected by the answers to each question.

···

On May 27, 2016, at 10:55 AM, Thorsten Seitz via swift-evolution <swift-evolution@swift.org> wrote:

We could just write

let x: P & Q
instead of
let x: Any<P, Q>

let x: Collection where .Element: P
instead of
let x: Any<Collection where .Element: P>

let x: P & Q where P.T == Q.T
instead of
let x: Any<P, Q where P.T == Q.T>

let x: P & Q & R
instead of
let x: Any<P, Q, R>

let x: Collection
instead of
let x: Any<Collection>

This would avoid the confusion of Any<T1, T2> being something completely different than a generic type (i.e. order of T1, T2 does not matter whereas for generic types it is essential).

-Thorsten

Am 26.05.2016 um 20:11 schrieb Adrian Zubarev via swift-evolution <swift-evolution@swift.org>:

Something like type<…> was considered at the very start of the whole discussion (in this thread), but it does not solve the meaning of an existential type and also might lead to even more confusion.

From my perspective I wouldn’t use parentheses here because it looks more like an init without any label Type.init(…) or Type(…). I could live with Any[…] but this doesn’t look shiny and Swifty to me. Thats only my personal view. :wink:

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:48:04, Vladimir.S via swift-evolution (swift-evolution@swift.org) schrieb:

Don't think {} is better here, as they also have "established meaning in
Swift today".

How about just Type(P1 & P2 | P3) - as IMO we can think of such
construction as "creation" of new type and `P1 & P2 | P3` could be treated
as parameters to initializer.

func f(t: Type(P1 & P2 | P3)) {..}

On 26.05.2016 20:32, L. Mihalkovic via swift-evolution wrote:
> How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.
>
>> On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org> wrote:
>>
>>
>>> on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org> wrote:
>>>
>>> There is great feedback going on here. I'd like to consider a few things here:
>>>
>>> * What if we name the whole thing `Existential<>` to sort out all
>>> confusion?
>>
>> Some of us believe that “existential” is way too theoretical a word to
>> force into the official lexicon of Swift. I think “Any<...>” is much
>> more conceptually accessible.
>>
>>>
>>> This would allow `typealias Any = Existential<>`. * Should
>>> `protocol A: Any<class>` replace `protocol A: class`? Or at least
>>> deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
>>> want to use any class requirement existential directly? If second, we
>>> will need to allow direct existential usage on protocols (right now we
>>> only can use typealiases as a worksround).
>>
>> --
>> Dave
>>
>> _______________________________________________
>> swift-evolution mailing list
>> swift-evolution@swift.org
>> https://lists.swift.org/mailman/listinfo/swift-evolution
> _______________________________________________
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


(Vladimir) #11

Btw, in case we have `where` keyword in syntax related to types/protocols (when defining constrains. and not some symbol like '>>'.. don't know, for example), why we can't have 'and' keyword also when discuss the syntax of type/protocol conjunction?
I.e.

let x: P and Q
let x: P and Q where P.T == Q.T
let x: P and Q and R

or, for consistency, as I understand it, we should have
let x: P & Q >> P.T == Q.T

···

On 27.05.2016 11:55, Thorsten Seitz via swift-evolution wrote:

We could just write

let x: P & Q
instead of
let x: Any<P, Q>

let x: Collection where .Element: P
instead of
let x: Any<Collection where .Element: P>

let x: P & Q where P.T == Q.T
instead of
let x: Any<P, Q where P.T == Q.T>

let x: P & Q & R
instead of
let x: Any<P, Q, R>

let x: Collection
instead of
let x: Any<Collection>

This would avoid the confusion of Any<T1, T2> being something completely
different than a generic type (i.e. order of T1, T2 does not matter whereas
for generic types it is essential).

-Thorsten

Am 26.05.2016 um 20:11 schrieb Adrian Zubarev via swift-evolution
<swift-evolution@swift.org <mailto:swift-evolution@swift.org>>:

Something like |type<…>| was considered at the very start of the whole
discussion (in this thread
<https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160502/016523.html>),
but it does not solve the meaning of an existential type and also might
lead to even more confusion.

From my perspective I wouldn’t use parentheses here because it looks more
like an init without any label |Type.init(…)| or |Type(…)|. I could live
with |Any[…]| but this doesn’t look shiny and Swifty to me. Thats only my
personal view. :wink:

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:48:04, Vladimir.S via swift-evolution
(swift-evolution@swift.org <mailto:swift-evolution@swift.org>) schrieb:

Don't think {} is better here, as they also have "established meaning in
Swift today".

How about just Type(P1 & P2 | P3) - as IMO we can think of such
construction as "creation" of new type and `P1 & P2 | P3` could be treated
as parameters to initializer.

func f(t: Type(P1 & P2 | P3)) {..}

On 26.05.2016 20:32, L. Mihalkovic via swift-evolution wrote:
> How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.
>
>> On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
>>
>>> on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
>>>
>>> There is great feedback going on here. I'd like to consider a few things here:
>>>
>>> * What if we name the whole thing `Existential<>` to sort out all
>>> confusion?
>>
>> Some of us believe that “existential” is way too theoretical a word to
>> force into the official lexicon of Swift. I think “Any<...>” is much
>> more conceptually accessible.
>>
>>>
>>> This would allow `typealias Any = Existential<>`. * Should
>>> `protocol A: Any<class>` replace `protocol A: class`? Or at least
>>> deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
>>> want to use any class requirement existential directly? If second, we
>>> will need to allow direct existential usage on protocols (right now we
>>> only can use typealiases as a worksround).
>>
>> --
>> Dave
>>
>> _______________________________________________
>> swift-evolution mailing list
>> swift-evolution@swift.org <mailto:swift-evolution@swift.org>
>> https://lists.swift.org/mailman/listinfo/swift-evolution
> _______________________________________________
> swift-evolution mailing list
> swift-evolution@swift.org <mailto:swift-evolution@swift.org>
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


(Matthew Johnson) #12

Personally I think `&` is more lightweight (and it is established in other languages like Ceylon and Typescript) and `where` is more expressive (and established in Swift for introducing constraints), so I would stay with these.

I agree. If we can make `&` with `where` work syntactically it would be nice to go in this lighter weight direction. If we decide to do that the question then becomes what to do with `protocol`. Would it be feasible to replace it with `&` in Swift 3 if we decide on that direction?

···

On May 27, 2016, at 8:18 AM, Thorsten Seitz via swift-evolution <swift-evolution@swift.org> wrote:

-Thorsten

Am 27.05.2016 um 14:34 schrieb Vladimir.S <svabox@gmail.com <mailto:svabox@gmail.com>>:

Btw, in case we have `where` keyword in syntax related to types/protocols (when defining constrains. and not some symbol like '>>'.. don't know, for example), why we can't have 'and' keyword also when discuss the syntax of type/protocol conjunction?
I.e.

let x: P and Q
let x: P and Q where P.T == Q.T
let x: P and Q and R

or, for consistency, as I understand it, we should have
let x: P & Q >> P.T == Q.T

On 27.05.2016 11:55, Thorsten Seitz via swift-evolution wrote:

We could just write

let x: P & Q
instead of
let x: Any<P, Q>

let x: Collection where .Element: P
instead of
let x: Any<Collection where .Element: P>

let x: P & Q where P.T == Q.T
instead of
let x: Any<P, Q where P.T == Q.T>

let x: P & Q & R
instead of
let x: Any<P, Q, R>

let x: Collection
instead of
let x: Any<Collection>

This would avoid the confusion of Any<T1, T2> being something completely
different than a generic type (i.e. order of T1, T2 does not matter whereas
for generic types it is essential).

-Thorsten

Am 26.05.2016 um 20:11 schrieb Adrian Zubarev via swift-evolution
<swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>>:

Something like |type<…>| was considered at the very start of the whole
discussion (in this thread
<https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160502/016523.html>),
but it does not solve the meaning of an existential type and also might
lead to even more confusion.

From my perspective I wouldn’t use parentheses here because it looks more
like an init without any label |Type.init(…)| or |Type(…)|. I could live
with |Any[…]| but this doesn’t look shiny and Swifty to me. Thats only my
personal view. :wink:

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:48:04, Vladimir.S via swift-evolution
(swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>) schrieb:

Don't think {} is better here, as they also have "established meaning in
Swift today".

How about just Type(P1 & P2 | P3) - as IMO we can think of such
construction as "creation" of new type and `P1 & P2 | P3` could be treated
as parameters to initializer.

func f(t: Type(P1 & P2 | P3)) {..}

On 26.05.2016 20:32, L. Mihalkovic via swift-evolution wrote:
> How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.
>
>> On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>> wrote:
>>
>>
>>> on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>> wrote:
>>>
>>> There is great feedback going on here. I'd like to consider a few things here:
>>>
>>> * What if we name the whole thing `Existential<>` to sort out all
>>> confusion?
>>
>> Some of us believe that “existential” is way too theoretical a word to
>> force into the official lexicon of Swift. I think “Any<...>” is much
>> more conceptually accessible.
>>
>>>
>>> This would allow `typealias Any = Existential<>`. * Should
>>> `protocol A: Any<class>` replace `protocol A: class`? Or at least
>>> deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
>>> want to use any class requirement existential directly? If second, we
>>> will need to allow direct existential usage on protocols (right now we
>>> only can use typealiases as a worksround).
>>
>> --
>> Dave
>>
>> _______________________________________________
>> swift-evolution mailing list
>> swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
>> https://lists.swift.org/mailman/listinfo/swift-evolution
> _______________________________________________
> swift-evolution mailing list
> swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


(Thorsten Seitz) #13

From the point of view of the type system `P & Q` is an anonymous supertype of `P` and `Q`.
This would be just the same if the syntax was `Any<P, Q>`. I don’t see a semantic difference here.

Whether that is a "container“ or not seems to be an implementation detail to me but should have nothing to do with the type system.
In what way should it be "lossy“?

Am I missing something?

-Thorsten

···

Am 27.05.2016 um 12:30 schrieb L. Mihalkovic <laurent.mihalkovic@gmail.com>:

It seem to me we are debating the how of a what that has not been defined. The root question behind all these alternatives seems to be to decide if the existential-ness should be carried by a 'container' that is then refined internally, or derived from the presence of the free-floating refinements. This is the question that splits the possible syntaxes into these 2 groups:

Any<> Any[]
Type<> Type<>
Existential<>

and the (these are all straw man representations that should not limit the thinking)

P & Q
@P and @Q
is P , Q
P & Q typed

If the answer is to use a 'container' then the next question is to see its relationship to the other existing containers: is it the result of a transformation, is it a superset, or a super type; it is obviously lossy, but not entirely if the solution follows in some of Brent's past suggestion to make some existential types instantiate-able (which opens a very similar problem to what java faced for several years when trying to identify a universal collection literal syntax).
That will narrow down the field of possible matches... until one syntax emerges as conveying the meaning that is reflected by the answers to each question.

On May 27, 2016, at 10:55 AM, Thorsten Seitz via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

We could just write

let x: P & Q
instead of
let x: Any<P, Q>

let x: Collection where .Element: P
instead of
let x: Any<Collection where .Element: P>

let x: P & Q where P.T == Q.T
instead of
let x: Any<P, Q where P.T == Q.T>

let x: P & Q & R
instead of
let x: Any<P, Q, R>

let x: Collection
instead of
let x: Any<Collection>

This would avoid the confusion of Any<T1, T2> being something completely different than a generic type (i.e. order of T1, T2 does not matter whereas for generic types it is essential).

-Thorsten

Am 26.05.2016 um 20:11 schrieb Adrian Zubarev via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>>:

Something like type<…> was considered at the very start of the whole discussion (in this thread <https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160502/016523.html>), but it does not solve the meaning of an existential type and also might lead to even more confusion.

From my perspective I wouldn’t use parentheses here because it looks more like an init without any label Type.init(…) or Type(…). I could live with Any[…] but this doesn’t look shiny and Swifty to me. Thats only my personal view. :wink:

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:48:04, Vladimir.S via swift-evolution (swift-evolution@swift.org <mailto:swift-evolution@swift.org>) schrieb:

Don't think {} is better here, as they also have "established meaning in
Swift today".

How about just Type(P1 & P2 | P3) - as IMO we can think of such
construction as "creation" of new type and `P1 & P2 | P3` could be treated
as parameters to initializer.

func f(t: Type(P1 & P2 | P3)) {..}

On 26.05.2016 20:32, L. Mihalkovic via swift-evolution wrote:
> How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.
>
>> On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
>>
>>
>>> on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
>>>
>>> There is great feedback going on here. I'd like to consider a few things here:
>>>
>>> * What if we name the whole thing `Existential<>` to sort out all
>>> confusion?
>>
>> Some of us believe that “existential” is way too theoretical a word to
>> force into the official lexicon of Swift. I think “Any<...>” is much
>> more conceptually accessible.
>>
>>>
>>> This would allow `typealias Any = Existential<>`. * Should
>>> `protocol A: Any<class>` replace `protocol A: class`? Or at least
>>> deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
>>> want to use any class requirement existential directly? If second, we
>>> will need to allow direct existential usage on protocols (right now we
>>> only can use typealiases as a worksround).
>>
>> --
>> Dave
>>
>> _______________________________________________
>> swift-evolution mailing list
>> swift-evolution@swift.org <mailto:swift-evolution@swift.org>
>> https://lists.swift.org/mailman/listinfo/swift-evolution
> _______________________________________________
> swift-evolution mailing list
> swift-evolution@swift.org <mailto:swift-evolution@swift.org>
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution


(Thorsten Seitz) #14

Personally I think `&` is more lightweight (and it is established in other languages like Ceylon and Typescript) and `where` is more expressive (and established in Swift for introducing constraints), so I would stay with these.

-Thorsten

···

Am 27.05.2016 um 14:34 schrieb Vladimir.S <svabox@gmail.com>:

Btw, in case we have `where` keyword in syntax related to types/protocols (when defining constrains. and not some symbol like '>>'.. don't know, for example), why we can't have 'and' keyword also when discuss the syntax of type/protocol conjunction?
I.e.

let x: P and Q
let x: P and Q where P.T == Q.T
let x: P and Q and R

or, for consistency, as I understand it, we should have
let x: P & Q >> P.T == Q.T

On 27.05.2016 11:55, Thorsten Seitz via swift-evolution wrote:

We could just write

let x: P & Q
instead of
let x: Any<P, Q>

let x: Collection where .Element: P
instead of
let x: Any<Collection where .Element: P>

let x: P & Q where P.T == Q.T
instead of
let x: Any<P, Q where P.T == Q.T>

let x: P & Q & R
instead of
let x: Any<P, Q, R>

let x: Collection
instead of
let x: Any<Collection>

This would avoid the confusion of Any<T1, T2> being something completely
different than a generic type (i.e. order of T1, T2 does not matter whereas
for generic types it is essential).

-Thorsten

Am 26.05.2016 um 20:11 schrieb Adrian Zubarev via swift-evolution
<swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>>:

Something like |type<…>| was considered at the very start of the whole
discussion (in this thread
<https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160502/016523.html>),
but it does not solve the meaning of an existential type and also might
lead to even more confusion.

From my perspective I wouldn’t use parentheses here because it looks more
like an init without any label |Type.init(…)| or |Type(…)|. I could live
with |Any[…]| but this doesn’t look shiny and Swifty to me. Thats only my
personal view. :wink:

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:48:04, Vladimir.S via swift-evolution
(swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>) schrieb:

Don't think {} is better here, as they also have "established meaning in
Swift today".

How about just Type(P1 & P2 | P3) - as IMO we can think of such
construction as "creation" of new type and `P1 & P2 | P3` could be treated
as parameters to initializer.

func f(t: Type(P1 & P2 | P3)) {..}

On 26.05.2016 20:32, L. Mihalkovic via swift-evolution wrote:
> How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.
>
>> On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>> wrote:
>>
>>
>>> on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>> wrote:
>>>
>>> There is great feedback going on here. I'd like to consider a few things here:
>>>
>>> * What if we name the whole thing `Existential<>` to sort out all
>>> confusion?
>>
>> Some of us believe that “existential” is way too theoretical a word to
>> force into the official lexicon of Swift. I think “Any<...>” is much
>> more conceptually accessible.
>>
>>>
>>> This would allow `typealias Any = Existential<>`. * Should
>>> `protocol A: Any<class>` replace `protocol A: class`? Or at least
>>> deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
>>> want to use any class requirement existential directly? If second, we
>>> will need to allow direct existential usage on protocols (right now we
>>> only can use typealiases as a worksround).
>>
>> --
>> Dave
>>
>> _______________________________________________
>> swift-evolution mailing list
>> swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
>> https://lists.swift.org/mailman/listinfo/swift-evolution
> _______________________________________________
> swift-evolution mailing list
> swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution


(Thorsten Seitz) #15

Personally I think `&` is more lightweight (and it is established in other languages like Ceylon and Typescript) and `where` is more expressive (and established in Swift for introducing constraints), so I would stay with these.

I agree. If we can make `&` with `where` work syntactically it would be nice to go in this lighter weight direction. If we decide to do that the question then becomes what to do with `protocol`. Would it be feasible to replace it with `&` in Swift 3 if we decide on that direction?

Yep. `protocol` should be replaced with `&` in that case.

-Thorsten

···

Am 27.05.2016 um 16:54 schrieb Matthew Johnson <matthew@anandabits.com>:

On May 27, 2016, at 8:18 AM, Thorsten Seitz via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

-Thorsten

Am 27.05.2016 um 14:34 schrieb Vladimir.S <svabox@gmail.com <mailto:svabox@gmail.com>>:

Btw, in case we have `where` keyword in syntax related to types/protocols (when defining constrains. and not some symbol like '>>'.. don't know, for example), why we can't have 'and' keyword also when discuss the syntax of type/protocol conjunction?
I.e.

let x: P and Q
let x: P and Q where P.T == Q.T
let x: P and Q and R

or, for consistency, as I understand it, we should have
let x: P & Q >> P.T == Q.T

On 27.05.2016 11:55, Thorsten Seitz via swift-evolution wrote:

We could just write

let x: P & Q
instead of
let x: Any<P, Q>

let x: Collection where .Element: P
instead of
let x: Any<Collection where .Element: P>

let x: P & Q where P.T == Q.T
instead of
let x: Any<P, Q where P.T == Q.T>

let x: P & Q & R
instead of
let x: Any<P, Q, R>

let x: Collection
instead of
let x: Any<Collection>

This would avoid the confusion of Any<T1, T2> being something completely
different than a generic type (i.e. order of T1, T2 does not matter whereas
for generic types it is essential).

-Thorsten

Am 26.05.2016 um 20:11 schrieb Adrian Zubarev via swift-evolution
<swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>>:

Something like |type<…>| was considered at the very start of the whole
discussion (in this thread
<https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160502/016523.html>),
but it does not solve the meaning of an existential type and also might
lead to even more confusion.

From my perspective I wouldn’t use parentheses here because it looks more
like an init without any label |Type.init(…)| or |Type(…)|. I could live
with |Any[…]| but this doesn’t look shiny and Swifty to me. Thats only my
personal view. :wink:

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:48:04, Vladimir.S via swift-evolution
(swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>) schrieb:

Don't think {} is better here, as they also have "established meaning in
Swift today".

How about just Type(P1 & P2 | P3) - as IMO we can think of such
construction as "creation" of new type and `P1 & P2 | P3` could be treated
as parameters to initializer.

func f(t: Type(P1 & P2 | P3)) {..}

On 26.05.2016 20:32, L. Mihalkovic via swift-evolution wrote:
> How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.
>
>> On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>> wrote:
>>
>>
>>> on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>> wrote:
>>>
>>> There is great feedback going on here. I'd like to consider a few things here:
>>>
>>> * What if we name the whole thing `Existential<>` to sort out all
>>> confusion?
>>
>> Some of us believe that “existential” is way too theoretical a word to
>> force into the official lexicon of Swift. I think “Any<...>” is much
>> more conceptually accessible.
>>
>>>
>>> This would allow `typealias Any = Existential<>`. * Should
>>> `protocol A: Any<class>` replace `protocol A: class`? Or at least
>>> deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
>>> want to use any class requirement existential directly? If second, we
>>> will need to allow direct existential usage on protocols (right now we
>>> only can use typealiases as a worksround).
>>
>> --
>> Dave
>>
>> _______________________________________________
>> swift-evolution mailing list
>> swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
>> https://lists.swift.org/mailman/listinfo/swift-evolution
> _______________________________________________
> swift-evolution mailing list
> swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution


(Austin Zheng) #16

Here's a strawman idea.

What if we go with '&' and 'where', but we enclose the whole thing in parentheses?

(class & Protocol1 & Protocol2 where .Foo == Int, .Bar : Baz)

There are a couple of reasons I propose this syntax:

- It makes it very clear where the definition of the type begins and ends. I understand people really despise angle brackets, but I really want some way to visually delineate the boundaries of the type. Plus, I imagine it makes syntax a little easier to parse and preemptively forbids some ambiguities.

- It's a structural, not nominal, type, like a tuple, so it uses parens as well. This reserves "<" and ">" for generic types.

- The '&' is easily understood - "Protocol1" *and* "Protocol2". It's also a signal that order doesn't matter - just like how order matters with things that use commas, like argument lists, tuples, and array members, order doesn't generally matter with bitwise or logical 'and' operators.

- If we ever decide to have union types, we have a very elegant third form of nominal type syntax that naturally falls out: (MyClass1 | MyClass2 | MyClass3).

Thoughts?

Austin

···

On May 27, 2016, at 9:07 AM, Thorsten Seitz via swift-evolution <swift-evolution@swift.org> wrote:

Am 27.05.2016 um 16:54 schrieb Matthew Johnson <matthew@anandabits.com <mailto:matthew@anandabits.com>>:

On May 27, 2016, at 8:18 AM, Thorsten Seitz via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

Personally I think `&` is more lightweight (and it is established in other languages like Ceylon and Typescript) and `where` is more expressive (and established in Swift for introducing constraints), so I would stay with these.

I agree. If we can make `&` with `where` work syntactically it would be nice to go in this lighter weight direction. If we decide to do that the question then becomes what to do with `protocol`. Would it be feasible to replace it with `&` in Swift 3 if we decide on that direction?

Yep. `protocol` should be replaced with `&` in that case.

-Thorsten

-Thorsten

Am 27.05.2016 um 14:34 schrieb Vladimir.S <svabox@gmail.com <mailto:svabox@gmail.com>>:

Btw, in case we have `where` keyword in syntax related to types/protocols (when defining constrains. and not some symbol like '>>'.. don't know, for example), why we can't have 'and' keyword also when discuss the syntax of type/protocol conjunction?
I.e.

let x: P and Q
let x: P and Q where P.T == Q.T
let x: P and Q and R

or, for consistency, as I understand it, we should have
let x: P & Q >> P.T == Q.T

On 27.05.2016 11:55, Thorsten Seitz via swift-evolution wrote:

We could just write

let x: P & Q
instead of
let x: Any<P, Q>

let x: Collection where .Element: P
instead of
let x: Any<Collection where .Element: P>

let x: P & Q where P.T == Q.T
instead of
let x: Any<P, Q where P.T == Q.T>

let x: P & Q & R
instead of
let x: Any<P, Q, R>

let x: Collection
instead of
let x: Any<Collection>

This would avoid the confusion of Any<T1, T2> being something completely
different than a generic type (i.e. order of T1, T2 does not matter whereas
for generic types it is essential).

-Thorsten

Am 26.05.2016 um 20:11 schrieb Adrian Zubarev via swift-evolution
<swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>>:

Something like |type<…>| was considered at the very start of the whole
discussion (in this thread
<https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160502/016523.html>),
but it does not solve the meaning of an existential type and also might
lead to even more confusion.

From my perspective I wouldn’t use parentheses here because it looks more
like an init without any label |Type.init(…)| or |Type(…)|. I could live
with |Any[…]| but this doesn’t look shiny and Swifty to me. Thats only my
personal view. :wink:

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:48:04, Vladimir.S via swift-evolution
(swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>) schrieb:

Don't think {} is better here, as they also have "established meaning in
Swift today".

How about just Type(P1 & P2 | P3) - as IMO we can think of such
construction as "creation" of new type and `P1 & P2 | P3` could be treated
as parameters to initializer.

func f(t: Type(P1 & P2 | P3)) {..}

On 26.05.2016 20:32, L. Mihalkovic via swift-evolution wrote:
> How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.
>
>> On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>> wrote:
>>
>>
>>> on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>> wrote:
>>>
>>> There is great feedback going on here. I'd like to consider a few things here:
>>>
>>> * What if we name the whole thing `Existential<>` to sort out all
>>> confusion?
>>
>> Some of us believe that “existential” is way too theoretical a word to
>> force into the official lexicon of Swift. I think “Any<...>” is much
>> more conceptually accessible.
>>
>>>
>>> This would allow `typealias Any = Existential<>`. * Should
>>> `protocol A: Any<class>` replace `protocol A: class`? Or at least
>>> deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
>>> want to use any class requirement existential directly? If second, we
>>> will need to allow direct existential usage on protocols (right now we
>>> only can use typealiases as a worksround).
>>
>> --
>> Dave
>>
>> _______________________________________________
>> swift-evolution mailing list
>> swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
>> https://lists.swift.org/mailman/listinfo/swift-evolution
> _______________________________________________
> swift-evolution mailing list
> swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


(Austin Zheng) #17

I think the parentheses are the fundamental aspect of the suggestion :).

Let me turn the question around. If tuples were declared like this:

let myTuple : Int, String, Bool = (10, "hello", false)

would the type be more or less readable? I find it a lot more difficult to immediately parse than:

let myTuple : (Int, String, Bool) = (10, "hello", false)

At the same time, nobody's complained about tuple type parentheses getting in the way.

We're trying to establish a syntax that will hopefully be used for things significantly more complicated than tuple definitions, which are just a list of types. I think readability is a major concern. Typealiases should be supported, but they shouldn't be required to make the feature useable.

Finally, wouldn't we need some delimiter for nested existential definitions anyways? Now you have the confusing situation where the outside definition has no delimiters, but the inside ones do:

// Why does the inner existential look fundamentally different than the outer one?
// Not to mention, visually parsing the boundaries of this type when you look at it in a function signature
let x : Protocol1, Protocol2, (Protocol 3 where .Foo == Int) where Protocol2.Bar : Baz

I hope that explains my reasoning.

Best,
Austin

···

On May 27, 2016, at 9:28 AM, Matthew Johnson <matthew@anandabits.com> wrote:

Sent from my iPad

On May 27, 2016, at 11:18 AM, Austin Zheng <austinzheng@gmail.com <mailto:austinzheng@gmail.com>> wrote:

Here's a strawman idea.

What if we go with '&' and 'where', but we enclose the whole thing in parentheses?

(class & Protocol1 & Protocol2 where .Foo == Int, .Bar : Baz)

There are a couple of reasons I propose this syntax:

- It makes it very clear where the definition of the type begins and ends. I understand people really despise angle brackets, but I really want some way to visually delineate the boundaries of the type. Plus, I imagine it makes syntax a little easier to parse and preemptively forbids some ambiguities.

- It's a structural, not nominal, type, like a tuple, so it uses parens as well. This reserves "<" and ">" for generic types.

- The '&' is easily understood - "Protocol1" *and* "Protocol2". It's also a signal that order doesn't matter - just like how order matters with things that use commas, like argument lists, tuples, and array members, order doesn't generally matter with bitwise or logical 'and' operators.

- If we ever decide to have union types, we have a very elegant third form of nominal type syntax that naturally falls out: (MyClass1 | MyClass2 | MyClass3).

Thoughts?

Generally in favor. But I would not require the parentheses. I believe they would be allowed optionally automatically, just as (Int) is the same as Int (because single element tuples don't exist and the underlying type is used directly instead). It seems better to leave parentheses up to a matter of style.

Austin

On May 27, 2016, at 9:07 AM, Thorsten Seitz via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

Am 27.05.2016 um 16:54 schrieb Matthew Johnson <matthew@anandabits.com <mailto:matthew@anandabits.com>>:

On May 27, 2016, at 8:18 AM, Thorsten Seitz via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

Personally I think `&` is more lightweight (and it is established in other languages like Ceylon and Typescript) and `where` is more expressive (and established in Swift for introducing constraints), so I would stay with these.

I agree. If we can make `&` with `where` work syntactically it would be nice to go in this lighter weight direction. If we decide to do that the question then becomes what to do with `protocol`. Would it be feasible to replace it with `&` in Swift 3 if we decide on that direction?

Yep. `protocol` should be replaced with `&` in that case.

-Thorsten

-Thorsten

Am 27.05.2016 um 14:34 schrieb Vladimir.S <svabox@gmail.com <mailto:svabox@gmail.com>>:

Btw, in case we have `where` keyword in syntax related to types/protocols (when defining constrains. and not some symbol like '>>'.. don't know, for example), why we can't have 'and' keyword also when discuss the syntax of type/protocol conjunction?
I.e.

let x: P and Q
let x: P and Q where P.T == Q.T
let x: P and Q and R

or, for consistency, as I understand it, we should have
let x: P & Q >> P.T == Q.T

On 27.05.2016 11:55, Thorsten Seitz via swift-evolution wrote:

We could just write

let x: P & Q
instead of
let x: Any<P, Q>

let x: Collection where .Element: P
instead of
let x: Any<Collection where .Element: P>

let x: P & Q where P.T == Q.T
instead of
let x: Any<P, Q where P.T == Q.T>

let x: P & Q & R
instead of
let x: Any<P, Q, R>

let x: Collection
instead of
let x: Any<Collection>

This would avoid the confusion of Any<T1, T2> being something completely
different than a generic type (i.e. order of T1, T2 does not matter whereas
for generic types it is essential).

-Thorsten

Am 26.05.2016 um 20:11 schrieb Adrian Zubarev via swift-evolution
<swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>>:

Something like |type<…>| was considered at the very start of the whole
discussion (in this thread
<https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160502/016523.html>),
but it does not solve the meaning of an existential type and also might
lead to even more confusion.

From my perspective I wouldn’t use parentheses here because it looks more
like an init without any label |Type.init(…)| or |Type(…)|. I could live
with |Any[…]| but this doesn’t look shiny and Swifty to me. Thats only my
personal view. :wink:

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:48:04, Vladimir.S via swift-evolution
(swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>) schrieb:

Don't think {} is better here, as they also have "established meaning in
Swift today".

How about just Type(P1 & P2 | P3) - as IMO we can think of such
construction as "creation" of new type and `P1 & P2 | P3` could be treated
as parameters to initializer.

func f(t: Type(P1 & P2 | P3)) {..}

On 26.05.2016 20:32, L. Mihalkovic via swift-evolution wrote:
> How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.
>
>> On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>> wrote:
>>
>>
>>> on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>> wrote:
>>>
>>> There is great feedback going on here. I'd like to consider a few things here:
>>>
>>> * What if we name the whole thing `Existential<>` to sort out all
>>> confusion?
>>
>> Some of us believe that “existential” is way too theoretical a word to
>> force into the official lexicon of Swift. I think “Any<...>” is much
>> more conceptually accessible.
>>
>>>
>>> This would allow `typealias Any = Existential<>`. * Should
>>> `protocol A: Any<class>` replace `protocol A: class`? Or at least
>>> deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
>>> want to use any class requirement existential directly? If second, we
>>> will need to allow direct existential usage on protocols (right now we
>>> only can use typealiases as a worksround).
>>
>> --
>> Dave
>>
>> _______________________________________________
>> swift-evolution mailing list
>> swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
>> https://lists.swift.org/mailman/listinfo/swift-evolution
> _______________________________________________
> swift-evolution mailing list
> swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org> <mailto:swift-evolution@swift.org <mailto:swift-evolution@swift.org>>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution


(Matthew Johnson) #18

From the point of view of the type system `P & Q` is an anonymous supertype of `P` and `Q`.
This would be just the same if the syntax was `Any<P, Q>`. I don’t see a semantic difference here.

Whether that is a "container“ or not seems to be an implementation detail to me but should have nothing to do with the type system.
In what way should it be "lossy“?

Am I missing something?

I was a bit confused as well and had to read this several times. I think this is talking about a syntactic “container” - i.e. brackets of some kind (as opposed to a “free floating” syntax). I don’t think it is talking about a semantic difference of any kind. But maybe I am still confused an not understanding what was intended...

···

On May 27, 2016, at 7:20 AM, Thorsten Seitz via swift-evolution <swift-evolution@swift.org> wrote:

-Thorsten

Am 27.05.2016 um 12:30 schrieb L. Mihalkovic <laurent.mihalkovic@gmail.com <mailto:laurent.mihalkovic@gmail.com>>:

It seem to me we are debating the how of a what that has not been defined. The root question behind all these alternatives seems to be to decide if the existential-ness should be carried by a 'container' that is then refined internally, or derived from the presence of the free-floating refinements. This is the question that splits the possible syntaxes into these 2 groups:

Any<> Any[]
Type<> Type<>
Existential<>

and the (these are all straw man representations that should not limit the thinking)

P & Q
@P and @Q
is P , Q
P & Q typed

If the answer is to use a 'container' then the next question is to see its relationship to the other existing containers: is it the result of a transformation, is it a superset, or a super type; it is obviously lossy, but not entirely if the solution follows in some of Brent's past suggestion to make some existential types instantiate-able (which opens a very similar problem to what java faced for several years when trying to identify a universal collection literal syntax).
That will narrow down the field of possible matches... until one syntax emerges as conveying the meaning that is reflected by the answers to each question.

On May 27, 2016, at 10:55 AM, Thorsten Seitz via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

We could just write

let x: P & Q
instead of
let x: Any<P, Q>

let x: Collection where .Element: P
instead of
let x: Any<Collection where .Element: P>

let x: P & Q where P.T == Q.T
instead of
let x: Any<P, Q where P.T == Q.T>

let x: P & Q & R
instead of
let x: Any<P, Q, R>

let x: Collection
instead of
let x: Any<Collection>

This would avoid the confusion of Any<T1, T2> being something completely different than a generic type (i.e. order of T1, T2 does not matter whereas for generic types it is essential).

-Thorsten

Am 26.05.2016 um 20:11 schrieb Adrian Zubarev via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>>:

Something like type<…> was considered at the very start of the whole discussion (in this thread <https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160502/016523.html>), but it does not solve the meaning of an existential type and also might lead to even more confusion.

From my perspective I wouldn’t use parentheses here because it looks more like an init without any label Type.init(…) or Type(…). I could live with Any[…] but this doesn’t look shiny and Swifty to me. Thats only my personal view. :wink:

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:48:04, Vladimir.S via swift-evolution (swift-evolution@swift.org <mailto:swift-evolution@swift.org>) schrieb:

Don't think {} is better here, as they also have "established meaning in
Swift today".

How about just Type(P1 & P2 | P3) - as IMO we can think of such
construction as "creation" of new type and `P1 & P2 | P3` could be treated
as parameters to initializer.

func f(t: Type(P1 & P2 | P3)) {..}

On 26.05.2016 20:32, L. Mihalkovic via swift-evolution wrote:
> How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.
>
>> On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
>>
>>
>>> on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
>>>
>>> There is great feedback going on here. I'd like to consider a few things here:
>>>
>>> * What if we name the whole thing `Existential<>` to sort out all
>>> confusion?
>>
>> Some of us believe that “existential” is way too theoretical a word to
>> force into the official lexicon of Swift. I think “Any<...>” is much
>> more conceptually accessible.
>>
>>>
>>> This would allow `typealias Any = Existential<>`. * Should
>>> `protocol A: Any<class>` replace `protocol A: class`? Or at least
>>> deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
>>> want to use any class requirement existential directly? If second, we
>>> will need to allow direct existential usage on protocols (right now we
>>> only can use typealiases as a worksround).
>>
>> --
>> Dave
>>
>> _______________________________________________
>> swift-evolution mailing list
>> swift-evolution@swift.org <mailto:swift-evolution@swift.org>
>> https://lists.swift.org/mailman/listinfo/swift-evolution
> _______________________________________________
> swift-evolution mailing list
> swift-evolution@swift.org <mailto:swift-evolution@swift.org>
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


(Matthew Johnson) #19

Personally I think `&` is more lightweight (and it is established in other languages like Ceylon and Typescript) and `where` is more expressive (and established in Swift for introducing constraints), so I would stay with these.

I agree. If we can make `&` with `where` work syntactically it would be nice to go in this lighter weight direction. If we decide to do that the question then becomes what to do with `protocol`. Would it be feasible to replace it with `&` in Swift 3 if we decide on that direction?

Yep. `protocol` should be replaced with `&` in that case.

Right, but it's a much larger syntax change. If we decide on that direction and it's not feasible for Swift 3 I suppose we would just leave 'protocol' alone until Swift 3.x or 4.

···

Sent from my iPad

On May 27, 2016, at 11:07 AM, Thorsten Seitz <tseitz42@icloud.com> wrote:

Am 27.05.2016 um 16:54 schrieb Matthew Johnson <matthew@anandabits.com>:
On May 27, 2016, at 8:18 AM, Thorsten Seitz via swift-evolution <swift-evolution@swift.org> wrote:

-Thorsten

-Thorsten

Am 27.05.2016 um 14:34 schrieb Vladimir.S <svabox@gmail.com>:

Btw, in case we have `where` keyword in syntax related to types/protocols (when defining constrains. and not some symbol like '>>'.. don't know, for example), why we can't have 'and' keyword also when discuss the syntax of type/protocol conjunction?
I.e.

let x: P and Q
let x: P and Q where P.T == Q.T
let x: P and Q and R

or, for consistency, as I understand it, we should have
let x: P & Q >> P.T == Q.T

On 27.05.2016 11:55, Thorsten Seitz via swift-evolution wrote:
We could just write

let x: P & Q
instead of
let x: Any<P, Q>

let x: Collection where .Element: P
instead of
let x: Any<Collection where .Element: P>

let x: P & Q where P.T == Q.T
instead of
let x: Any<P, Q where P.T == Q.T>

let x: P & Q & R
instead of
let x: Any<P, Q, R>

let x: Collection
instead of
let x: Any<Collection>

This would avoid the confusion of Any<T1, T2> being something completely
different than a generic type (i.e. order of T1, T2 does not matter whereas
for generic types it is essential).

-Thorsten

Am 26.05.2016 um 20:11 schrieb Adrian Zubarev via swift-evolution
<swift-evolution@swift.org <mailto:swift-evolution@swift.org>>:

Something like |type<…>| was considered at the very start of the whole
discussion (in this thread
<https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160502/016523.html>),
but it does not solve the meaning of an existential type and also might
lead to even more confusion.

From my perspective I wouldn’t use parentheses here because it looks more
like an init without any label |Type.init(…)| or |Type(…)|. I could live
with |Any[…]| but this doesn’t look shiny and Swifty to me. Thats only my
personal view. :wink:

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:48:04, Vladimir.S via swift-evolution
(swift-evolution@swift.org <mailto:swift-evolution@swift.org>) schrieb:

Don't think {} is better here, as they also have "established meaning in
Swift today".

How about just Type(P1 & P2 | P3) - as IMO we can think of such
construction as "creation" of new type and `P1 & P2 | P3` could be treated
as parameters to initializer.

func f(t: Type(P1 & P2 | P3)) {..}

On 26.05.2016 20:32, L. Mihalkovic via swift-evolution wrote:
> How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.
>
>> On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
>>
>>
>>> on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
>>>
>>> There is great feedback going on here. I'd like to consider a few things here:
>>>
>>> * What if we name the whole thing `Existential<>` to sort out all
>>> confusion?
>>
>> Some of us believe that “existential” is way too theoretical a word to
>> force into the official lexicon of Swift. I think “Any<...>” is much
>> more conceptually accessible.
>>
>>>
>>> This would allow `typealias Any = Existential<>`. * Should
>>> `protocol A: Any<class>` replace `protocol A: class`? Or at least
>>> deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
>>> want to use any class requirement existential directly? If second, we
>>> will need to allow direct existential usage on protocols (right now we
>>> only can use typealiases as a worksround).
>>
>> --
>> Dave
>>
>> _______________________________________________
>> swift-evolution mailing list
>> swift-evolution@swift.org <mailto:swift-evolution@swift.org>
>> https://lists.swift.org/mailman/listinfo/swift-evolution
> _______________________________________________
> swift-evolution mailing list
> swift-evolution@swift.org <mailto:swift-evolution@swift.org>
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


(Matthew Johnson) #20

Here's a strawman idea.

What if we go with '&' and 'where', but we enclose the whole thing in parentheses?

(class & Protocol1 & Protocol2 where .Foo == Int, .Bar : Baz)

There are a couple of reasons I propose this syntax:

- It makes it very clear where the definition of the type begins and ends. I understand people really despise angle brackets, but I really want some way to visually delineate the boundaries of the type. Plus, I imagine it makes syntax a little easier to parse and preemptively forbids some ambiguities.

- It's a structural, not nominal, type, like a tuple, so it uses parens as well. This reserves "<" and ">" for generic types.

- The '&' is easily understood - "Protocol1" *and* "Protocol2". It's also a signal that order doesn't matter - just like how order matters with things that use commas, like argument lists, tuples, and array members, order doesn't generally matter with bitwise or logical 'and' operators.

- If we ever decide to have union types, we have a very elegant third form of nominal type syntax that naturally falls out: (MyClass1 | MyClass2 | MyClass3).

Thoughts?

Generally in favor. But I would not require the parentheses. I believe they would be allowed optionally automatically, just as (Int) is the same as Int (because single element tuples don't exist and the underlying type is used directly instead). It seems better to leave parentheses up to a matter of style.

···

Sent from my iPad

On May 27, 2016, at 11:18 AM, Austin Zheng <austinzheng@gmail.com> wrote:

Austin

On May 27, 2016, at 9:07 AM, Thorsten Seitz via swift-evolution <swift-evolution@swift.org> wrote:

Am 27.05.2016 um 16:54 schrieb Matthew Johnson <matthew@anandabits.com>:

On May 27, 2016, at 8:18 AM, Thorsten Seitz via swift-evolution <swift-evolution@swift.org> wrote:

Personally I think `&` is more lightweight (and it is established in other languages like Ceylon and Typescript) and `where` is more expressive (and established in Swift for introducing constraints), so I would stay with these.

I agree. If we can make `&` with `where` work syntactically it would be nice to go in this lighter weight direction. If we decide to do that the question then becomes what to do with `protocol`. Would it be feasible to replace it with `&` in Swift 3 if we decide on that direction?

Yep. `protocol` should be replaced with `&` in that case.

-Thorsten

-Thorsten

Am 27.05.2016 um 14:34 schrieb Vladimir.S <svabox@gmail.com>:

Btw, in case we have `where` keyword in syntax related to types/protocols (when defining constrains. and not some symbol like '>>'.. don't know, for example), why we can't have 'and' keyword also when discuss the syntax of type/protocol conjunction?
I.e.

let x: P and Q
let x: P and Q where P.T == Q.T
let x: P and Q and R

or, for consistency, as I understand it, we should have
let x: P & Q >> P.T == Q.T

On 27.05.2016 11:55, Thorsten Seitz via swift-evolution wrote:
We could just write

let x: P & Q
instead of
let x: Any<P, Q>

let x: Collection where .Element: P
instead of
let x: Any<Collection where .Element: P>

let x: P & Q where P.T == Q.T
instead of
let x: Any<P, Q where P.T == Q.T>

let x: P & Q & R
instead of
let x: Any<P, Q, R>

let x: Collection
instead of
let x: Any<Collection>

This would avoid the confusion of Any<T1, T2> being something completely
different than a generic type (i.e. order of T1, T2 does not matter whereas
for generic types it is essential).

-Thorsten

Am 26.05.2016 um 20:11 schrieb Adrian Zubarev via swift-evolution
<swift-evolution@swift.org <mailto:swift-evolution@swift.org>>:

Something like |type<…>| was considered at the very start of the whole
discussion (in this thread
<https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160502/016523.html>),
but it does not solve the meaning of an existential type and also might
lead to even more confusion.

From my perspective I wouldn’t use parentheses here because it looks more
like an init without any label |Type.init(…)| or |Type(…)|. I could live
with |Any[…]| but this doesn’t look shiny and Swifty to me. Thats only my
personal view. :wink:

--
Adrian Zubarev
Sent with Airmail

Am 26. Mai 2016 bei 19:48:04, Vladimir.S via swift-evolution
(swift-evolution@swift.org <mailto:swift-evolution@swift.org>) schrieb:

Don't think {} is better here, as they also have "established meaning in
Swift today".

How about just Type(P1 & P2 | P3) - as IMO we can think of such
construction as "creation" of new type and `P1 & P2 | P3` could be treated
as parameters to initializer.

func f(t: Type(P1 & P2 | P3)) {..}

On 26.05.2016 20:32, L. Mihalkovic via swift-evolution wrote:
> How about something like Type{P1 & P2 | P3} the point being that "<...>" has an established meaning in Swift today which is not what is expressed in the "<P1,P2,P3>" contained inside Any<P1, P2,P3>.
>
>> On May 26, 2016, at 7:11 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
>>
>>
>>> on Thu May 26 2016, Adrian Zubarev <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
>>>
>>> There is great feedback going on here. I'd like to consider a few things here:
>>>
>>> * What if we name the whole thing `Existential<>` to sort out all
>>> confusion?
>>
>> Some of us believe that “existential” is way too theoretical a word to
>> force into the official lexicon of Swift. I think “Any<...>” is much
>> more conceptually accessible.
>>
>>>
>>> This would allow `typealias Any = Existential<>`. * Should
>>> `protocol A: Any<class>` replace `protocol A: class`? Or at least
>>> deprecate it. * Do we need `typealias AnyClass = Any<class>` or do we
>>> want to use any class requirement existential directly? If second, we
>>> will need to allow direct existential usage on protocols (right now we
>>> only can use typealiases as a worksround).
>>
>> --
>> Dave
>>
>> _______________________________________________
>> swift-evolution mailing list
>> swift-evolution@swift.org <mailto:swift-evolution@swift.org>
>> https://lists.swift.org/mailman/listinfo/swift-evolution
> _______________________________________________
> swift-evolution mailing list
> swift-evolution@swift.org <mailto:swift-evolution@swift.org>
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution