如何在 Swift 中创建一个 ((NSErrorPointer -> NSData!)!) 闭包

How to make an ((NSErrorPointer -> NSData!)!) closure in Swift

我正在尝试使用 ZipZap 方法

ZZArchiveEntry(fileName: String!, compress: Bool, dataBlock: ((NSErrorPointer) -> NSData!)!)

在 Swift 中,但无法找出 dataBlock 闭包的正确语法。 我尝试了以下代码:

let fileEntry = ZZArchiveEntry(fileName: "test.txt", compress: true, dataBlock: {
            (error: NSErrorPointer) in
            return "test".dataUsingEncoding(NSUTF8StringEncoding)!
        })

这会导致以下错误:

Cannot find an initializer for type 'ZZArchiveEntry' that accepts an argument list of type '(fileName: String, compress: Bool, dataBlock: (NSErrorPointer) -> _)'

这样的关闭是否可能,如果是,在 Xcode 7.0 beta 3 中如何实现?

您可以使用 Swift 的尾随闭包语法,如下所示:

let fileEntry = ZZArchiveEntry(fileName: "test.txt", compress: true) { (error) -> NSData! in
    return ("test" as NSString).dataUsingEncoding(NSUTF8StringEncoding)!
}

或者更简单地说:

let fileEntry = ZZArchiveEntry(fileName: "test.txt", compress: true) { error in
    ("test" as NSString).dataUsingEncoding(NSUTF8StringEncoding)!
}

您还需要将 "test" 显式转换为 NSString 才能使用 dataUsingEncoding(_:) 方法。

对了,Xcode可以自动给你写闭包。对于 select 关闭,例如按下 Tab 按钮,您将看到:

然后按键盘上的回车键,Xcode会写入所有的括号和需要的参数。

您正在 return 一个未包装的可选 NSData(即您 return 一个非可选)并且编译器正在变得困惑。

您可以通过将值暂存在变量中来解决它:

let fileEntry = ZZArchiveEntry(fileName: "test.txt", compress: true, dataBlock: {
    (error: NSErrorPointer) in
    let data = "test".dataUsingEncoding(NSUTF8StringEncoding)!
    return data
})

或者,因为期望的 return 闭包类型是可选的,如果您删除 !,错误就会消失:

let fileEntry = ZZArchiveEntry(fileName: "test.txt", compress: true, dataBlock: {
    (error: NSErrorPointer) in
    return "test".dataUsingEncoding(NSUTF8StringEncoding)
})

或者,正如其他人所指出的,您可以进一步简化:

let fileEntry = ZZArchiveEntry(fileName: "test.txt", compress: true) { error in
    return "test".dataUsingEncoding(NSUTF8StringEncoding)
}