isEmpty
プロパティを含むようにスタックの種類を変更する必要があります。次に、pop
コールを複製する必要はなく、単純なwhile-let
ループになります。
guard !myStack.isEmpty else {
throw MyError.EmptyStack
}
while let nextVar = myStack.pop() {
// Process nextVar
}
またSequenceType
にこれを変換することができますが、その後、反復は、スタックを消費しません。そして、これは単に次のようになります。
guard !myStack.isEmpty else {
throw MyError.EmptyStack
}
for nextVar in myStack {
// Process nextVar
}
pop
がGeneratorType.next()
の正確必要な実装であるので、(generate()
でself
を返すことによって)GeneratorType
とSequenceType
にこれを有効にする簡単なはずです。
は値型であるため、for-in
でそれを反復処理すると、元のスタックを消費するのではなくコピーが作成され、そのコピーが消費されます。それは良いか悪いか。ここで
は私が何を意味するかのスケッチです:
struct Stack<Element> {
private var stack: [Element] = []
mutating func push(element: Element) {
stack.append(element)
}
mutating func pop() -> Element? {
guard let result = stack.last else { return nil }
stack.removeLast()
return result
}
var isEmpty: Bool { return stack.isEmpty }
}
extension Stack: GeneratorType {
mutating func next() -> Element? {
return pop()
}
}
extension Stack: SequenceType {
func generate() -> Stack {
return self
}
}
マイナー発言:あなたはSequenceType *と* generatorTypeを両方を採用した場合、あなたは(生成実装する必要はありません)、デフォルトの実装があります。 –