Skip to content

Instantly share code, notes, and snippets.

@colbyn
Last active January 13, 2025 01:57
Show Gist options
  • Save colbyn/d78454c01d774f9f62415353c72cbce4 to your computer and use it in GitHub Desktop.
Save colbyn/d78454c01d774f9f62415353c72cbce4 to your computer and use it in GitHub Desktop.
Finalize Swift iterators into a given type
fileprivate func example() {
func wantsArray(array: [Int]) {
print("given:", array.debugDescription)
}
func wantsContiguousArray(array: ContiguousArray<Int>) {
print("given:", array.debugDescription)
}
let valuesIterator: IndexingIterator<Array<Int>> = [1, 2, 3, 4, 5, 6].makeIterator()
// MARK: THIS DOES NOT WORK:
// wantsArray(array: values)
// ^^^^^^
// TYPE ERROR:
// Cannot convert value of type 'IndexingIterator<Array<Int>>' to expected argument type '[Int]'
// MARK: But the following works:
wantsArray(array: valuesIterator.finalize(as: Array.self)) // GOOD
wantsContiguousArray(array: valuesIterator.finalize(as: ContiguousArray.self)) // GOOD
}
// MARK: - implementation -
extension Sequence {
func finalize<Into: FromSequence>(as type: Into.Type) -> Into where Into.Element == Self.Element {
return Into.init(fromSequence: self)
}
}
protocol FromSequence {
init(fromSequence sequence: some Sequence<Element>)
associatedtype Element
}
extension Array: FromSequence {
init(fromSequence sequence: some Sequence<Element>) {
self.init(sequence)
}
typealias Element = Self.Element
}
extension ContiguousArray: FromSequence {
init(fromSequence sequence: some Sequence<Element>) {
self.init(sequence)
}
typealias Element = Self.Element
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment