【发布时间】:2017-05-19 09:02:54
【问题描述】:
将要描述的问题与我之前的问题有关: string.withCString and UnsafeMutablePointer(mutating: cstring) wrapped into a function 这是我处理 nil 字符串的第一种方法(通过将 withCString 放入函数中) 对于 Mecki 提出的一个问题: Why can't I pass an optional Swift String to C function that allows NULL pointers?
想象有一个像这样的 c 函数:
unsigned long randomSign(char *pin, char *tag_signature, char *tag_data, char *xyz);
如果我在相应的 swift 函数周围包裹 4 个 string.withCString 闭包,我知道该函数可以正常工作:
// pin, tag_signature, tag_data and xyz are optional Strings so they may be nil which is a problem for my result.
// corresponding swift function:
// randomSign(pin: UnsafeMutablePointer<Int8>!, tag_signature: UnsafeMutablePointer<Int8>!, tag_data: UnsafeMutablePointer<Int8>!, xyz: UnsafeMutablePointer<Int8>!)
let result = pin.withCString { s1 in return
tag_signature.withCString {s2 in return
tag_data.withCString {s3 in return
xyz.withCString { s4 in return
randomSign(UnsafeMutablePointer(mutating: s1), UnsafeMutablePointer(mutating: s2), UnsafeMutablePointer(mutating: s3), UnsafeMutablePointer(mutating: s4))
}}}}
And so Martin R replied to an easier example,不需要将闭包包裹在 randomSign(arguments) 和 UnsafeMutablePointer(mutating: ...) 周围,因为它也可以获取字符串并进行转换。 但是当我放弃闭包并将其用作Martin R described 时,它在启动mac 后直接在模拟器上首次启动时工作,但是在连续调用randomSign-Function 时,返回会告诉我例如tag_signature 或pin 将是无效的(但它实际上是有效的,我不知道为什么?!)。
这导致我需要 withCString 闭包(目前)但我必须处理 nil-Strings 的问题,这将导致应用程序在返回结果时崩溃,因为它无法评估 randomSign -函数。
所以我尝试让the approach below (also suggested by @Martin R) 适应 Swift 3,但我没有努力适应它。
//Swift-2 written by Martin R
protocol CStringConvertible {
func withCString<Result>(@noescape f: UnsafePointer<Int8> throws -> Result) rethrows -> Result
}
extension String: CStringConvertible { }
extension Optional where Wrapped: CStringConvertible {
func withOptionalCString<Result>(@noescape f: UnsafePointer<Int8> -> Result) -> Result {
if let string = self {
return string.withCString(f)
} else {
return f(nil)
}
}
}
//Swift 3: ???
如果有人能告诉我,为什么我的函数只在我使用 withCString 时有效,而在我关闭它时无效,我将不胜感激 以及是否有人知道如何解决该问题,即将 swift-2 代码正确转换为可工作的 swift-3 代码。
【问题讨论】:
标签: c swift interop unsafe-pointers