Created
July 31, 2017 20:53
-
-
Save jemmons/d3ca0e29ae3b913ce1c42b21790d807c to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import Foundation | |
public struct CartesianProductIterator<X, Y>: IteratorProtocol where X: IteratorProtocol, Y: Collection { | |
private var xIt: X | |
private let yCol: Y | |
private var x: X.Element? | |
private var yIt: Y.Iterator | |
public init(xs: X, ys: Y) { | |
xIt = xs | |
yCol = ys | |
x = xIt.next() | |
yIt = yCol.makeIterator() | |
} | |
public typealias Element = (X.Element, Y.Element) | |
public mutating func next() -> Element? { | |
guard !yCol.isEmpty else { | |
return nil | |
} | |
guard let someX = x else { | |
return nil | |
} | |
guard let someY = yIt.next() else { | |
yIt = yCol.makeIterator() | |
x = xIt.next() | |
return next() | |
} | |
return (someX, someY) | |
} | |
} | |
public struct CartesianProductSequence<X, Y>: Sequence where X: Sequence, Y: Collection { | |
public typealias Iterator = CartesianProductIterator<X.Iterator, Y> | |
private let xs: X | |
private let ys: Y | |
public init(xs: X, ys: Y) { | |
self.xs = xs | |
self.ys = ys | |
} | |
public func makeIterator() -> Iterator { | |
return Iterator(xs: xs.makeIterator(), ys: ys) | |
} | |
} | |
public func product<X, Y>(_ xs: X, _ ys: Y) -> CartesianProductSequence<X, Y> where X: Sequence, Y: Collection { | |
return CartesianProductSequence(xs: xs, ys: ys) | |
} | |
// USAGE: | |
let xs = 1...10 | |
let ys = ["A", "B", "C", "D", "E", | |
"F", "G", "H", "I", "J"] | |
product(xs, ys).forEach { x, y in | |
print(x) | |
print(y) | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment