问题
I need a function that returns a lazy generator of various composed generator functions such as filter and map. For example, if I want to apply lazy.filter().map()
the code looks like:
// Simplified
typealias MyComplexType = Int
typealias MyComplexCollection = [MyComplexType]
func selection() -> LazyMapCollection<LazyFilterCollection<MyComplexCollection>, Int> {
let objects:MyComplexCollection = [1, 2, 3, 4, 5, 6]
let result = objects.lazy.filter({$0 < 4}).map({$0 * 10})
return result
}
for obj in someObjects() {
print(obj)
}
Is there a more generic way to specify the LazyMapCollection<LazyFilterCollection<MyComplexCollection>, Int>
? I tried LazyGenerator<MyComplexCollection>
but I'm getting type incompatibility error. Chaining more lazy functions would make the type even more complex. Better and more appropriate for my needs would be to have a type similar to just LazySomething<MyComplexType>
.
回答1:
Yes!
What you want exists, and even has a fancy name: "type-erasure"
Swift has some structs that exist to forward calls on, but not expose (as much of) the underlaying type:
- AnyBidirectionalCollection
- AnyBidirectionalIndex
- AnyForwardCollection
- AnyForwardIndex
- AnyGenerator
- AnyRandomAccessCollection
- AnyRandomAccessIndex
- AnySequence
So you want something like
func selection() -> AnySequence<MyComplexType> {
let objects:MyComplexCollection = [1, 2, 3, 4, 5, 6]
let result = objects.lazy.filter({$0 < 4}).map({$0 * 10})
return AnySequence(result)
}
(because your call to say subscript(2) is forwarded the laziness is preserved, which is sometimes good, sometimes bad)
However AnyForwardCollection might work out better in practice because it will be missing many of the methods that trip people up when using lazy collections.
来源:https://stackoverflow.com/questions/33382765/generic-lazycollection-type