代码之家  ›  专栏  ›  技术社区  ›  Brandon M

swift数据子集崩溃

  •  0
  • Brandon M  · 技术社区  · 6 年前

    每当我试图对数据对象进行子集划分时,都会遇到崩溃。我找到了解决问题的办法,但我不明白为什么必须这样做才能帮助解决问题。

    我有一个长度正好是1000字节的数据对象。

    我有一系列的结构,这些结构会将该对象转发到另一个结构的初始值设定项。

    struct DataHeader {
      let headerVal1: UInt16
      let headerVal2: UInt32
    
      init(withData: Data) {
        var offset = 0
        var length = MemoryLayout<UInt16>.size
        headerVal1 = uint16Value(data: withData[offset..<length])
    
        offset = length
        length = MemoryLayout<UInt32>.size + offset
        headerVal2 = uint32Value(data: withData[offset..<length])
      }
    }
    
    struct DataBlock {
      let dataVal1: UInt8
      let dataVal2: UInt32
      let dataVal3: Float
    
      init(withData: Data) {
        var offset = 0
        var length = MemoryLayout<UInt8>.size
        dataVal1 = uint8Value(data: withData[offset..<length])
    
        offset = length
        length = MemoryLayout<UInt32>.size + offset
        dataVal2 = uint32Value(data: withData[offset..<length]) // <-- CRASH
    
        offset = length
        length = MemoryLayout<Float>.size + offset
        dataVal3 = floatValue(data: withData[offset..<length])
      }
    }
    
    struct EntireData {
      let header: DataHeader
      let block: DataBlock
      // etc. continues for several other structures
    
      init(withData: Data) {
        var offset = 0
        var length = MemoryLayout<DataHeader>.size
    
        header = DataHeader(withData: withData[offset..<length])
    
        offset = length
        length = MemoryLayout<DataBlock>.size
        block = DataBlock(withData: withData[offset..<length])
      }
    }
    

    …在另一个代码块中,从文件加载数据并传递到 EntireData .

    注意,第一次发生是好的。在代码持续一段时间后发生崩溃。

    我不明白的是,我问这个问题的原因是,我找到了一个解决办法。基本上,不用 withData 在构造函数中,复制如下:

    let unnecessaryDataCopy = withData.advanced(by: 0)
    

    然后,使用 unnecessaryDataCopy 代替 有数据 作为函数调用参数,没有问题。系统对完全相同的数据执行。我知道那里有数据,因为有几百个字节要空闲。

    我觉得仅仅为了访问数据就必须复制两份数据是不对的。(其中一个 .advanced(by: 0) 还有一个有子集([偏移量..<长度])。

    为什么在没有不必要的数据拷贝的情况下会崩溃?我该怎么做才能使它变得更好?谢谢!

    0 回复  |  直到 6 年前