文档说:“当一个函数被声明为接受一个 UnsafeMutablePointer 参数时,它可以接受以下任何一个......一个 in-out 表达式,其操作数是一个存储的 Type 类型的左值,它作为地址传递的左值。” 我可以复制示例并进行演示。
func takesAMutablePointer<T>(x: UnsafeMutablePointer<T>) -> UnsafeMutablePointer<T>
{
return x
}
func useAMutablePointer()
{
var legInt :UInt32 = 42
var legIntArray: [UInt32] = [legInt]
var legIntPtr: UnsafeMutablePointer<UInt32>
legIntPtr = takesAMutablePointer(&legInt)
legIntPtr = takesAMutablePointer(&legIntArray)
legIntPtr = UnsafeMutablePointer(&legInt) //Compile error!
legIntPtr = UnsafeMutablePointer(&legIntArray) //Compile error!
}
Xcode 显示 UnsafeMutablePointer 具有以下初始化程序:
init<U>(_ from: UnsafeMutablePointer<U>)
,但是当我尝试像我的函数一样使用它时,编译器错误是 Cannot find an initializer for type 'UnsafeMutablePointer<T>' that accepts an argument list of type '(inout UInt32)'
所以,
- 获得
UnsafeMutablePointer<UInt32>
的直接方法是什么?到 legInt? - 为什么我不能按预期使用初始化器?
谢谢!
最佳答案
我在这里有点猜测,但原因似乎是
UnsafeMutablePointer<T>
具有通用初始化器
init<U>(_ from: UnsafeMutablePointer<U>)
哪里<U>
与 <T>
无关.编译器好像不能
推断类型 <U>
在
legIntPtr = UnsafeMutablePointer(&legInt) //Compile error!
为了证实这个猜想,我们可以定义一个自定义扩展
extension UnsafeMutablePointer {
init(_ from : UnsafeMutablePointer<T>) {
// Swift 2: init(_ from : UnsafeMutablePointer<Memory>) {
self = from
}
}
从相同类型的另一个指针初始化指针。 现在您的所有代码都可以按预期编译和工作。
你可以做的是使用 withUnsafeMutablePointer()
:
legIntPtr = withUnsafeMutablePointer(&legInt, { $0 })
但请记住,编译器不会跟踪指向的指针
对象作为引用,并可能破坏该对象。这就是为什么
这些指针是“不安全的”。您通常应该使用指针
仅在 withUnsafeMutablePointer()
关闭。
关于swift - 为什么我不能用 (&myUInt32) 或 (&[myUInt32]) 初始化 Swift UnsafeMutablePointer<UInt32>,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29976346/