2016-12-23 10 views
1

최근 단위 테스트를 사용하여 내가 작성한 객체가 올바르게 할당되지 않았는지 확인하려고했습니다. 그러나 테스트를 완료하기 전에 객체를 시도해도 객체의 할당을 해제하지 않았 음을 알았습니다. 그래서 약한 변수를 사용하여 객체 할당 해제의 기초를 증명하려는 간단한 예제 (아래 참조)로 테스트를 축소했습니다.Swift XCTest : 약한 변수의 적절한 할당 해제 확인

내 생각에 강한 참조는 테스트 메소드가 종료 된 후에도 객체를 유지하지 않아야하며 약한 참조는 다음 실행 루프에서 참조 될 때 nil이어야합니다. 그러나 약한 참조는 결코 0이 아니며 두 테스트가 모두 실패합니다. 내가 여기서 뭔가를 오해하니? 아래는 전체 단위 테스트입니다.

class Mock { //class type, should behave with reference semantics 

    init() { } 
} 

class DeallocationTests: XCTestCase { 

    func testWeakVarDeallocation() { 

     let strongMock = Mock() 

     weak var weakMock: Mock? = strongMock 

     let expt = expectation(description: "deallocated") 

     DispatchQueue.main.async { 

      XCTAssertNil(weakMock)  //This assertion fails 

      expt.fulfill() 
     } 

     waitForExpectations(timeout: 1.0, handler: nil) 
    } 

    func testCaptureListDeallocation() { 

     let strongMock = Mock() 

     let expt = expectation(description: "deallocated") 

     DispatchQueue.main.async { [weak weakMock = strongMock] in 

      XCTAssertNil(weakMock)  //This assertion also fails 

      expt.fulfill() 
     } 

     waitForExpectations(timeout: 1.0, handler: nil) 
    } 
} 

나는 아마 해제가 XCTest에 의해 어떻게 든 연기하지만, 심지어 객체가 할당 해제 발생하지 않았던 autoreleasepool의 시험 방법 몸을 감싸는되었다는 생각했다.

+0

'할 필요가 weakMock' 옵션, 예를 들어, 약한 약한 약한 모자 : 모의? = strongMock'. 'nil'으로 설정할 수 없다면 해제 할 수 없습니다. – par

+0

@par'weakMock'은 컴파일러에 의해 강제로 자동 선택됩니다. 'weakMock'의 타입을 검사하면 명시 적 타입 주석없이'Mock? '이됩니다. –

+0

그리고 명시 적으로 선택하면 선택 사항이 없습니까? – par

답변

3

strongMock에 대한 강력한 참조가 유지되도록 dispatchAsync 블록이 호출 될 때 testWeakVarDeallocation() 함수가 종료되지 않는 것이 문제입니다.

합니다 (종료 testWeakVarDeallocation() 허용)과 같이 그것을 시도하고 당신은 weakMock 예상대로 nil을하게 볼 수 있습니다 :

class weakTestTests: XCTestCase { 
    var strongMock: Mock? = Mock() 

    func testWeakVarDeallocation() { 
     weak var weakMock = strongMock 

     print("weakMock is \(weakMock)") 

     let expt = self.expectation(description: "deallocated") 

     strongMock = nil 

     print("weakMock is now \(weakMock)") 

     DispatchQueue.main.async { 
      XCTAssertNil(weakMock)  // This assertion fails 

      print("fulfilling expectation") 
      expt.fulfill() 
     } 

     print("waiting for expectation") 
     self.waitForExpectations(timeout: 1.0, handler: nil) 
     print("expectation fulfilled") 
    } 
} 
+0

오브젝트가 할당 해제되지 않는 이유는 옳았지만 해결책으로 문제가 해결되지 않습니다. 대기중인 기대가 없으므로 첫 번째 비동기 블록이 실행되기 전에 테스트가 완료되고 통과합니다. 꽤 잡기 22. –

+0

맞습니다. XCTest 함수는 기다리지 않습니다. 나는 대답을 업데이트했고 그것은 지금 옳은 일을한다. – par

+0

그래, 그게 아래의 문제를 해결 autoreleasepool을 사용하여 알아 냈어,하지만 귀하의 솔루션은 본질적으로 동일합니다. 도와 주셔서 감사합니다! –