> On Dec 29, 2015, at 12:06 PM, Kevin Ballard via swift-evolution > <[email protected]> wrote: > > I briefly skimmed your proposal, so I apologize if you already addressed > this, but it occurs to me that we could support automatic protocol forwarding > today on a per-protocol basis simply by declaring a separate protocol that > provides default implementations doing the forwarding. Handling of Self > return types can then be done by adding a required initializer (or just not > implementing that method, so the concrete type is forced to deal with it even > though everything else is forwarded). > > For example, if I want to automatically forward SequenceType to a member, I > can do something like > > protocol SequenceTypeForwarder : SequenceType { > typealias ForwardedSequenceType : SequenceType > > var forwardedSequence : ForwardedSequenceType { get } > } > > extension SequenceTypeForwarder { > func generate() -> ForwardedSequenceType.Generator { > return forwardedSequence.generate() > } > > func underestimateCount() -> Int { > return forwardedSequence.underestimateCount() > } > > func map<T>(@noescape transform: > (ForwardedSequenceType.Generator.Element) throws -> T) rethrows -> [T] { > return try forwardedSequence.map(transform) > } > > func filter(@noescape includeElement: > (ForwardedSequenceType.Generator.Element) throws -> Bool) rethrows -> > [ForwardedSequenceType.Generator.Element] { > return try forwardedSequence.filter(includeElement) > } > > func forEach(@noescape body: (ForwardedSequenceType.Generator.Element) > throws -> Void) rethrows { > return try forwardedSequence.forEach(body) > } > > func dropFirst(n: Int) -> ForwardedSequenceType.SubSequence { > return forwardedSequence.dropFirst(n) > } > > func dropLast(n: Int) -> ForwardedSequenceType.SubSequence { > return forwardedSequence.dropLast(n) > } > > func prefix(maxLength: Int) -> ForwardedSequenceType.SubSequence { > return forwardedSequence.prefix(maxLength) > } > > func suffix(maxLength: Int) -> ForwardedSequenceType.SubSequence { > return forwardedSequence.suffix(maxLength) > } > > func split(maxSplit: Int, allowEmptySlices: Bool, @noescape isSeparator: > (ForwardedSequenceType.Generator.Element) throws -> Bool) rethrows -> > [ForwardedSequenceType.SubSequence] { > return try forwardedSequence.split(maxSplit, allowEmptySlices: > allowEmptySlices, isSeparator: isSeparator) > } > }
FWIW, https://github.com/apple/swift/blob/master/stdlib/public/core/SequenceWrapper.swift Though I don’t know why we still have this; it’s not used anywhere and should probably be removed. I think it was supposed to be part of the new lazy sequence/collection subsystem but it was never incorporated. > With this protocol declared, I can then say something like > > struct Foo { > var ary: [Int] > } > > extension Foo : SequenceTypeForwarder { > var forwardedSequence: [Int] { return ary } > } > > and my struct Foo now automatically implements SequenceType by forwarding to > its variable `ary`. > > The downside to this is it needs to be manually declared for each protocol. > But I wager that most protocols actually aren't really amenable to forwarding > anyway. > > -Kevin Ballard > > _______________________________________________ > swift-evolution mailing list > [email protected] > https://lists.swift.org/mailman/listinfo/swift-evolution
_______________________________________________ swift-evolution mailing list [email protected] https://lists.swift.org/mailman/listinfo/swift-evolution
