You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

为何以UnsafeRawPointer传递结构体时需基于var而非let?

为什么Data.init(bytes:,count:)要求用var而非let变量取地址?

首先要明确:Swift里的&操作符,不管目标函数参数是UnsafeRawPointer还是inout,它的语义是创建一个临时的inout绑定——这个绑定规则要求被取地址的变量必须是可变的(var),哪怕函数本身不会通过指针修改内存。

具体到Data的初始化方法

虽然Data.init(bytes: UnsafeRawPointer, count: Int)接收的是不可变指针,但Swift的安全模型不会去验证函数内部是否真的会修改指针指向的内容。只要你用&取地址,编译器就会默认这个操作可能会修改变量,因此强制要求变量是var类型,否则就会抛出「Cannot pass immutable value as inout」的错误。

用let变量的替代方案

如果想用let定义的不可变变量生成Data,可以用withUnsafePointer(to:)显式获取不可变指针,这个API专门适配不可变变量的场景,编译器能确认不会修改内存,因此允许使用let:

let immutableCopy = instanceOfA
let data = withUnsafePointer(to: immutableCopy) { ptr in
    Data(bytes: ptr, count: MemoryLayout.size(ofValue: instanceOfA))
}

核心原因总结

  • &操作符的inout绑定规则是根本:它要求变量可变,不管目标参数是否是不可变指针。
  • withUnsafePointer(to:)是Swift提供的、针对不可变变量取指针的合法途径,绕过了&的var限制。

内容的提问来源于stack exchange,提问作者Theis Egeberg

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.19 00:30:54