[swift-evolution] [Pitch] Generalized supertype constraints

Dennis Weissmann dennis at dennisweissmann.me
Sat Nov 25 17:26:32 CST 2017


You’re right, I misunderstood that paragraph (maybe I read what I wanted to read :D). Thank you very much for the clarification and I’ll take a closer look at your proposal tomorrow!

- Dennis

Sent from my iPhone

> On 25. Nov 2017, at 10:37 PM, Adrian Zubarev <adrian.zubarev at devandartist.com> wrote:
> 
> Well no, this proposal won’t allow your example. The problem in your example actually has different roots - *Metatypes*. As by today, meta types are somehow broken, especially in generic / associated type context. Furthermore there is currently no way to express that you may want a subtype for an existential metatype instead of the static metatype.
> 
> For more informations about meta types and who some of us would like them to work, read our proposal here:
> https://github.com/DevAndArtist/swift-evolution/blob/refactor_existential_metatypes/proposals/0126-refactor-metatypes.md
> 
> Then your example could be expressed as:
> 
> ```
> func register<S>(_ service: Service, ofType type: Type<S>) where AnyType<S> : AnyType<Service> {}
> 
> // or if I’m not mistaken we can make use if implicit existential like this then
> func register<S>(_ service: Service, ofType type: Type<S>) where S : Service {}
> ```
> 
> I don't want to dive any deeper about the metatype pain points, because I don’t want to prevent the success of the pitched idea with an off-topic.
> 
> 
> Am 25. November 2017 um 16:34:58, Dennis Weissmann (dennis at dennisweissmann.me) schrieb:
> 
>> I would also love to have generic associated types in the language, I have a lot of uses for them and, IIUC, supertype constraint would enable me to express the following:
>> 
>> protocol Service {}
>> 
>> protocol WikiService: Service {} // methods not shown for conciseness
>> class DefaultWikiService: WikiService {}
>> class DemoWikiService: WikiService {}
>> 
>> class DataServiceManager {
>> 
>>     private var registry = [String: Service]()
>> 
>>     func register<S>(_ service: Service, ofType type: S.Type) where S: Service {
>>         let key = "\(Swift.type(of: type))"
>>         registry[key] = service
>>     }
>> 
>>     func service<S>(ofType type: S.Type) -> S where S: Service {
>>         let key = "\(Swift.type(of: type))"
>> 
>>         // It is a programmer error to expect a value for a not yet registered type
>>         guard let service = registry[key] as? S else {
>>             fatalError("Service of type \(type) cannot be found. Please register a service for that type before accessing it.")
>>         }
>>         return service
>>     }
>> 
>> }
>> 
>> let manager = DataServiceManager()
>> if isDemoMode {
>>     manager.register(DemoWikiService(), ofType: WikiService.self) // Currently: error: in argument type 'WikiService.Protocol', 'WikiService' does not conform to expected type 'Service'
>> } else {
>>     manager.register(DefaultWikiService(), ofType: WikiService.self) // Currently: error: in argument type 'WikiService.Protocol', 'WikiService' does not conform to expected type 'Service'
>> }
>> 
>> If that's right, I'm also +1 on this :)
>> 
>> - Dennis
>> 
>>> On Nov 25, 2017, at 12:13 AM, Adrian Zubarev via swift-evolution <swift-evolution at swift.org> wrote:
>>> 
>>> In general this is more then welcome, so +1 for me.
>>> 
>>> However I have one question:
>>> 
>>> Could this allow support, or at least be a first step towards Swift allowing the following behaviour?
>>> 
>>> ```
>>> extension MyProtocol where Self : SomeClass {
>>> static func getSubtypes<T>(ofType _: T.Type = T.self) -> [T] where T : Self { ... }
>>> }
>>> ```
>>> 
>>> I would like to be able to upgrade `Self` to a class constraint, which then will allow me to only accept subtypes from T at compile time.
>>> 
>>> Am 25. November 2017 um 00:03:23, Matthew Johnson via swift-evolution (swift-evolution at swift.org) schrieb:
>>> 
>>>> One of the most frequent frustrations I encounter when writing generic code in Swift is the requirement that supertype constraints be concrete.  When I mentioned this on Twitter (https://twitter.com/anandabits/status/929958479598534656) Doug Gregor mentioned that this feature is smaller and mostly straightforward to design and implement (https://twitter.com/dgregor79/status/929975472779288576). 
>>>> 
>>>> I currently have a PR open to add the high-level description of this feature found below to the generics manifesto (https://github.com/apple/swift/pull/13012):
>>>> 
>>>> Currently, supertype constraints may only be specified using a concrete class or protocol type.  This prevents us from abstracting over the supertype.
>>>> 
>>>> ```swift
>>>> protocol P {
>>>>   associatedtype Base
>>>>   associatedtype Derived: Base
>>>> }
>>>> ```
>>>> 
>>>> In the above example `Base` may be any type.  `Derived` may be the same as `Base` or may be _any_ subtype of `Base`.  All subtype relationships supported by Swift should be supported in this context including, but not limited to, classes and subclasses, existentials and conforming concrete types or refining existentials, `T?` and  `T`, `((Base) -> Void)` and `((Derived) -> Void)`, etc.
>>>> 
>>>> Generalized supertype constraints would be accepted in all syntactic locations where generic constraints are accepted.
>>>> 
>>>> I would like to see generalized supertype constraints make it into Swift 5 if possible.  I am not an implementer so I will not be able to bring a proposal forward alone but am interested in collaborating with anyone interested in working on implementation.
>>>> 
>>>> I am also interested in hearing general feedback on this feature from the community at large.  Have you also found this limitation frustrating?  In what contexts?  Does anyone have reservations about introducing this capability?  If so, what are they?
>>>> 
>>>> Matthew
>>>> 
>>>> _______________________________________________
>>>> swift-evolution mailing list
>>>> swift-evolution at swift.org
>>>> https://lists.swift.org/mailman/listinfo/swift-evolution
>>> _______________________________________________
>>> swift-evolution mailing list
>>> swift-evolution at swift.org
>>> https://lists.swift.org/mailman/listinfo/swift-evolution
>> 
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://lists.swift.org/pipermail/swift-evolution/attachments/20171126/37e60633/attachment.html>


More information about the swift-evolution mailing list