[swift-evolution] [Review] SE-0052: Change IteratorType post-nil guarantee

Gwendal Roué gwendal.roue at gmail.com
Fri Apr 29 03:20:44 CDT 2016


> Le 29 avr. 2016 à 08:18, Gwendal Roué <gwendal.roue at gmail.com> a écrit :
> 
>> The review of "SE-0052: Change IteratorType post-nil guarantee" begins now and runs through May 3. The proposal is available here:
>> 
>> 	https://github.com/apple/swift-evolution/blob/master/proposals/0052-iterator-post-nil-guarantee.md <https://github.com/apple/swift-evolution/blob/master/proposals/0052-iterator-post-nil-guarantee.md>
> I'd thus […] support the following alternatives:
> 
> - the FuseIterator Patrick's proposal (and we could discuss its name).
> - a new StoppingIterator protocol which does explicitly provide the post-nil guarantee. Algorithms could then use this guarantee.

Actually, a StoppingIterator protocol is not a good idea, because this concept should go up the type hierarchy up to Collection in order to let sequence and collection methods use static type information in order to choose the correct iterator algorithm.

I'd prefer a FuseIterator that eventually returns nil forever as soon as it underlying iterator returns nil. Yes, fuseIterator would not apply the "when calling next(), no preceding call to next() should have returned nil" precondition. This precondition would be removed from the Iterator documentation. The FuseIterator would be the easy-going iterator, the one that has no surprise, and makes it easy to write algorithms.

When one needs a "simple" iterator, one just has to derive a FuseIterator from it. Its implementation could look like:

struct FuseIterator<Element> : Iterator {
    let baseNext: () -> Element?
    var ended: Bool = false
    init<I: Iterator where G.Element == Element>(_ baseIterator: I) {
        var baseIterator = baseIterator
        baseNext = { baseIterator.next() }
    }
    mutating func next() -> Element? {
        if ended {
            return nil
        } else if let element = baseNext() {
            return element
        } else {
            ended = true
            return nil
        }
    }
}

We would maybe also need a FuseSequence, in order to iterate a wild base iterator with a `for` loop until its first nil.

Last, forgive my non-native English, but when I look at "fuse" in a Thesaurus, I don't quite see the meaning of "consume until first exhaustion". It looks like any one of "BoundedIterator", "ClosedIterator", "CompactIterator", "TerminatingIterator" would better communicate its nature. "ClosedIterator" looks like the new "ClosedRange" types introduced by SE-0065 and is my current favorite.

Gwendal Roué

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://lists.swift.org/pipermail/swift-evolution/attachments/20160429/1f909b31/attachment.html>


More information about the swift-evolution mailing list