2017-10-20 8 views
1

Swift(Objective-Cの過去6年間)にはかなり新しく、ブロック内のEnum値を評価するときには少し問題があります。これを実証する最善の方法は例です。これを使用するときにSwiftで定義されたブロック内で列挙型を評価する

enum MyType { 
    case type1 
    case type2 
} 

class MySuperClass { 
    var type: MyType 
    var object: SomeObject 

    init(param: SomeObject) { 
     self.type = .type1 
     self.object = param 
    } 

    public func doSomething(handler block: @escaping (AnyObject) -> Void) { 
     self.type = .type2 
     // assign handler block to property, blah blah 
     object.execHandler(forMethod: "testing", completion: { (response) -> Void in 
      block(response) 
     }) 
    } 

    public func reset() { 
     self.type = .type1 
    } 
} 

class MySubClass: MySuperClass { 

    override init(param: SomeObject) { 
     super.init(param: param) 

     let myBlock: MyBlockType = { (responseObject) -> Void in 
      // do some stuff 

      // ISSUE ARISES HERE 
      switch self.type { 
       case .type2: 
        print("Is type2") 
       default: 
        print("Do Nothing") 
      } 
     }; 
     object.addHandler(forMethod: "testing", processBlock: myBlock) 
    } 

} 

はその後、私は単にこのような何かやってる:見ることができるように

let myObject = MySubClass(param: passingInAnObject) // the block is defined and setup (this sets the 'type' to .type2) 
myObject.doSomething(handler: { (responseObject) -> Void in 
    print("completed") 
}) 
// do some other stuff 
// ... 
object.reset() 

を、doSomething方法はとき、しかし、.type2に列挙型を設定し、ブロックを実行しますブロックmyBlockが評価され、古い値が使用されます(.type1ではなく、.type2)。したがって、コード実行は常にprint("Do Nothing")行に分類されます。

私はSwiftの値によって列挙型がコピーされると信じていますので、このStackOverflowポスト(How to store a reference to an integer in Swift)に記載されているようにオブジェクトでこれらをラップしようとしましたが、無駄です。

これを克服する方法や、何か間違ったことをしている場合、私はいくつかアドバイスをいただきたいと思います。

+1

何かが非同期で実行された後に呼び出されると仮定して、 'myBlock'が実行される前に、おそらく' object.reset() 'を呼び出すでしょう。 – dan

+0

@danは、この厄介なことではありません。つまり、 'object.reset()'は補完ハンドラ内にあるはずです。本当に早くそれを見たことがあります。ありがとう!!! – Taz

答えて

0

Danのコメントに続いて調査した結果、非同期ブロックが実行される前にenum varが元の値にリセットされているように見えます。

関連する問題