enumerate function returns type EnumerateGenerator. But in Swift you are allowed to use that and assign to tuple. How does EnumerateGenerator become a tuple?
Definition: func enumerate<Seq : SequenceType>(seq: Seq) -> EnumerateGenerator<Seq.Generator>
for (index, value) in enumerate([1, 2, 3, 4, 5]) {
// How does EnumerateGenerator become a tuple?
}
In definition of EnumerateGenerator, Element is typealiased to a tuple, am I correct to assume that calling enumerate() is the same as calling EnumerateGenerator->next?
struct EnumerateGenerator<Base : GeneratorType> : GeneratorType, SequenceType {
typealias Element = (index: Int, element: Base.Element)
mutating func next() -> Element?
typealias Generator = EnumerateGenerator<Base>
func generate() -> EnumerateGenerator<Base>
}
From "For-In Statement" in the Swift documentation:
A for-in statement allows a block of code to be executed once for each item in a collection (or any type) that conforms to the SequenceType protocol.
The generate method is called on the collection expression to obtain a value of a generator type—that is, a type that conforms to the GeneratorType protocol. The program begins executing a loop by calling the next method on the stream. If the value returned is not None, it is assigned to the item pattern, the program executes the statements, and then continues execution at the beginning of the loop. Otherwise, the program does not perform assignment or execute the statements, and it is finished executing the for-in statement.
So
for (index, value) in enumerate([1, 2, 3, 4, 5]) {
// ...
}
is identical to
let enumGenerator = enumerate([1, 2, 3, 4, 5])
var genFunc = enumGenerator.generate()
while let (index, value) = genFunc.next() {
// ...
}
let enumGenerator = enumerate([1, 2, 3, 4, 5])
returns a
EnumerateGenerator<Seq.Generator>
(in this
case a EnumerateGenerator<IndexingGenerator<Array<Int>>>
). This conforms to the
SequenceType
protocol.
var genFunc = enumGenerator.generate()
returns again a
EnumerateGenerator<Seq.Generator>
(probably a copy of the enumGenerator
).
This conforms to the GeneratorType
protocol.
genFunc.next()
returns Element?
where Element
is a type alias for
(index: Int, element: Base.Element)
.
In this case, next()
returns (index: Int, element: Int)?
. This next function
returns optional tuples until the array is exhausted, where it returns nil
.