У меня есть метод, который ранее работал в Swift 3. Это порт алгоритма сжатия BZ.Метод выделяет память, сжимает ее и делает ее доступной во время выполнения.С Xcode 10.1 код не компилируется.Метод повторно оценивает память для запуска алгоритма, и это не разрешено в swift, но более строго в swift 4.
Вот сообщение об ошибке, которое я получаю в Xcode: перекрывающийся доступ к 'buff', но модификация требует монопольного доступа;рассмотрите возможность копирования в локальную переменную
var bzCompressedData: Data? {
get {
if self.count == 0 {
return self
}
var compressed = [UInt8]()
var stream = bz_stream()
var mself = self
var success = true
mself.withUnsafeMutableBytes { (selfBuff: UnsafeMutablePointer<Int8>) -> Void in
stream.next_in = selfBuff
stream.avail_in = UInt32(self.count)
var buff = Data(capacity: Int(BZCompressionBufferSize))
var copyBuff = buff
copyBuff.withUnsafeMutableBytes({ (outBuff: UnsafeMutablePointer<Int8>) -> Void in
stream.next_out = outBuff
stream.avail_out = BZCompressionBufferSize
var bzret = BZ2_bzCompressInit(&stream, BZDefaultBlockSize, 0, BZDefaultWorkFactor)
if bzret != BZ_OK {
print("failed compression init")
success = false
return
}
repeat {
bzret = BZ2_bzCompress(&stream, stream.avail_in > 0 ? BZ_RUN : BZ_FINISH)
if bzret < BZ_OK {
print("failed compress")
success = false
return
}
buff.withUnsafeBytes({ (bp: UnsafePointer<UInt8>) -> Void in
let bpp = UnsafeBufferPointer(
start: bp, count: (Int(BZCompressionBufferSize) - Int(stream.avail_out)))
compressed.append(contentsOf: bpp)
})
stream.next_out = outBuff
stream.avail_out = BZCompressionBufferSize
} while bzret != BZ_STREAM_END
})
}
BZ2_bzCompressEnd(&stream)
if !success {
return nil
}
return Data(bytes: compressed)
}
}
. Это позволяет разрешить компиляцию, но я вижу, что исходный буфер перераспределен и дает сбой во время выполнения.