【问题标题】:Initialize struct from Data in Swift 3在 Swift 3 中从数据初始化结构
【发布时间】:2017-09-14 15:03:22
【问题描述】:

我有一个名为MyContiguousStructStruct,其内存布局没有填充。

struct MyContiguousStruct {
    let ivar1: UInt8
    let ivar2: UInt8
    let ivar3: UInt16
    let ivar4: UInt16
}

我的初始化程序(很棒)像这样工作:

init?(data: Data) {
    guard data.count == MemoryLayout<Self>.size else { return nil }
    self = data.withUnsafeBytes { $0.pointee }
}

我决定将ivar1 的类型从UInt8 更改为具有rawValueUInt8 的枚举,如下所示:

struct MyContiguousStruct {
    let ivar1: EnumWithRawValueUInt8
    let ivar2: UInt8
    let ivar3: UInt16
    let ivar4: UInt16
}

但现在得到的似乎是初始化的MyContiguousStruct,但ivar1 不是初始化的枚举。我知道我可以逐字节读取数据,即:

ivar1 = data[0]
ivar2 = data[1]
// ...

但这意味着我不能将其放入可以附加到连续存储类型的协议中。如何确保枚举已初始化?

【问题讨论】:

  • 您将临时序列化格式与 Swift 使用的布局格式相结合。不要这样做,因为结构布局算法可以随时更改(例如实现压缩)

标签: swift struct enums initialization memory-layout


【解决方案1】:

我相信您将不得不手动解析它。枚举可以用原始值表示,但它们的底层 Type 不是那个值(就像在某些语言中那样)。添加的功能是遵守RawRepresentable 协议的结果,而不是通过更改类型或该类型的存储。

如果您不想手动解析数据,一个不错的解决方法是将ivar1 设为私有并为您的枚举提供一个计算属性。 例如

private let _ivar1: UInt8
var ivar1: EnumWithRawValueUInt8? {
    return EnumWithRawValueUInt8(rawValue: _ivar1)
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-11-21
    • 1970-01-01
    • 2021-01-31
    • 1970-01-01
    • 1970-01-01
    • 2017-07-21
    相关资源
    最近更新 更多