Skip to content

Instantly share code, notes, and snippets.

@khanlou
Created February 23, 2017 02:39
Show Gist options
  • Select an option

  • Save khanlou/0ee7195ddcd2a88211f26351d97712ed to your computer and use it in GitHub Desktop.

Select an option

Save khanlou/0ee7195ddcd2a88211f26351d97712ed to your computer and use it in GitHub Desktop.
```struct TreeNode<Element> {
var element: Element
var children: [TreeNode<Element>]
}
class TreeNodeIterator<Element>: IteratorProtocol {
var node: TreeNode<Element>
var index = -1
var currentIterator: TreeNodeIterator<Element>?
init(node: TreeNode<Element>) {
self.node = node
}
func next() -> Element? {
if index == -1 {
index = 0
if !node.children.isEmpty {
currentIterator = TreeNodeIterator(node: node.children[index])
}
return node.element
}
if index >= 0 && index < node.children.count {
if let next = currentIterator?.next() {
return next
} else {
index += 1
if index < node.children.count {
currentIterator = TreeNodeIterator(node: node.children[index])
return currentIterator?.next()
}
}
}
return nil
}
}
extension TreeNode: Sequence {
func makeIterator() -> TreeNodeIterator<Element> {
return TreeNodeIterator(node: self)
}
}
let node = TreeNode(element: 1, children: [
TreeNode(element: 2, children: [
TreeNode(element: 3, children: [])
]),
TreeNode(element: 4, children: []),
TreeNode(element: 5, children: [])
])
for child in node {
print(child)
}```
extension TreeNode: Sequence {
func makeIterator() -> AnyIterator<Element> {
var returnedSelf = false
var allChildrenIterator = children.makeIterator()
var currentChildIterator: AnyIterator<Element>?
return AnyIterator({
if !returnedSelf {
returnedSelf = true
return self.element
}
if let next = currentChildIterator?.next() {
return next
}
if let child = allChildrenIterator.next() {
currentChildIterator = child.makeIterator()
return currentChildIterator!.next()
}
return nil
})
}
}
extension TreeNode: SequenceType {
func generate() -> AnyGenerator<Element> {
let elementIterator = GeneratorOfOne(element)
let childrenGenerator = children.map({ $0.generate() }).flatten().generate()
let combinedIterator = CombineIterator(elementIterator, childrenGenerator)
return AnyGenerator(combinedIterator)
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment