[swift-evolution] [Review] SE-0102: Remove @noreturn attribute and introduce an empty NoReturn type

Anton Zhilin antonyzhilin at gmail.com
Fri Jun 24 11:01:51 CDT 2016


I can think of at least one example of using Never.
Suppose Stream protocol that returns a value at the end:

protocol Stream {
    associatedtype Element
    associatedtype Result

    mutable func next() -> Either<Element, Result>

Result can be used for information why the stream has stopped.
Calling next() after it returns Result is undefined behaviour.

You can easily see that Iterator is a special case of Stream
with Result = ().

Algorithms on IteratorWithResult should not drop the result:

func forEach<S>(stream: inout S,
                block: (S.Element) -> ())
                -> S.Result
                where S: Stream

We can split our Stream nicely:

func split<S>(stream: inout S,
              take: Int)
              -> TakePrefixStream
              where S: Stream

TakePrefixStream.Result is also a Stream, so to process two parts of 
stream differently, we do:

split(s, take: 10).forEach(calledOnFirstTen).forEach(calledOnOthers)

In the same spirit, we can split a stream into 3 or N parts.
Note that split itself does not take any elements from the Stream,
everything is lazy.

You've already noticed where Never has its place.
If a stream is infinite, we use Result = Never.

More information about the swift-evolution mailing list