将非托管<anyobject>与nil </anyobject>进行比较

时间:2014-10-27 18:06:31

标签: ios swift xcode6.1

从此博文中复制代码:http://matthewpalmer.net/blog/2014/06/21/example-ios-keychain-swift-save-query/

我以前有这段代码:

// Search for the keychain items
let status: OSStatus = SecItemCopyMatching(keychainQuery, &dataTypeRef)

// The following line crashes with an EXEC_BAD_ACCESS if dataTypeRef is nil
var opaque = dataTypeRef!.toOpaque()

当我使用钥匙串查询中的新帐户值运行上述操作时,dataTypeRef将为nil,从而导致EXEC_BAD_ACCESS

我试图通过检查dataTypeRef是否nil来避免这种情况:

var opaque = COpaquePointer.null()
if (dataTypeRef != nil) {
    opaque = dataTypeRef!.toOpaque()    // This line should not be executed.
}

虽然调试器显示dataTypeRefnil,但仍会输入if子句并崩溃。

有人能解释一下这里发生了什么吗?我确实有Objective-C的经验,但我无法弄清楚这里发生了什么。

1 个答案:

答案 0 :(得分:6)

据我所知,toOpaque/fromOpaque舞蹈不再是必要的,而你 可以简单地使用可选绑定。这可以与演员组合NSData 使用可选链接:

let status: OSStatus = SecItemCopyMatching(keychainQuery, &dataTypeRef)
if let retrievedData = dataTypeRef?.takeRetainedValue() as? NSData {
    contentsOfKeychain = NSString(data: retrievedData, encoding: NSUTF8StringEncoding)
}

另请注意takeRetainedValue()是正确的选择,因为您拥有&#34; SecItemCopyMatching返回的项目(其名称为&#34; Copy&#34;)。

但实际上你应该先检查返回值

let status: OSStatus = SecItemCopyMatching(keychainQuery, &dataTypeRef)
if status == errSecSuccess {
    if let retrievedData = dataTypeRef?.takeRetainedValue() as? NSData {
        contentsOfKeychain = NSString(data: retrievedData, encoding: NSUTF8StringEncoding)
    }
}