我正在为iOS
Swift中的shapefile构建一个自定义文件打开器(一种GIS格式,与此问题无关).这些文件有一个100字节长的标题.我能够将其读入4字节数组,存储我想要的信息.我可以将这些数组转换为Swift类型Data和NSData,并有一些其他选项可以转换它们(如Base64EncodedString).但是我无法将这些原始数组或数据或任何格式转换为有用的属性,如Double,Int和String.
import Foundation struct ShapeReader { var shapeFile = FileHandle(forReadingAtPath: "/Users/christopherjlowrie/Documents/Shapes/SF_Neighborhoods/Planning_Zones.shp") var fileHeader: String{ let header = shapeFile?.readData(ofLength: 100) let headerStream = InputStream(data: header!) headerStream.open() var buffer = [UInt8](repeating: 0,count: 4) while (headerStream.hasBytesAvailable){ headerStream.read(&buffer,maxLength: buffer.count) print(buffer) let x = Data(buffer) print(x) } return "A" } }
这当前只返回A,因为测试原因我返回一个字符串
如何打开文件,并将其原始字节读入Swift中的类型(双打,Ints,字符串)?
解决方法
你可以这样做:
要从String,Int或Double转换为数据:
Xcode 9•Swift 4 //对于旧的Swift 3语法单击here
extension String { var data: Data { return Data(utf8) } } extension Numeric { var data: Data { var source = self // This will return 1 byte for 8-bit,2 bytes for 16-bit,4 bytes for 32-bit and 8 bytes for 64-bit binary integers. For floating point types it will return 4 bytes for single-precision,8 bytes for double-precision and 16 bytes for extended precision. return Data(bytes: &source,count: MemoryLayout<Self>.size) } }
要从Data转换回String,Int或Double:
extension Data { var integer: Int { return withUnsafeBytes { $0.pointee } } var int32: Int32 { return withUnsafeBytes { $0.pointee } } var float: Float { return withUnsafeBytes { $0.pointee } } var float80: Float80 { return withUnsafeBytes { $0.pointee } } var double: Double { return withUnsafeBytes { $0.pointee } } var string: String { return String(data: self,encoding: .utf8) ?? "" } }
游乐场测试
let intData = 1_234_567_890_123_456_789.data // 8 bytes (64 bit Integer) let dataToInt = intData.integer // 1234567890123456789 let intMinData = Int.min.data // 8 bytes (64 bit Integer) let backToIntMin = intMinData.integer // -9223372036854775808 let intMaxData = Int.max.data // 8 bytes (64 bit Integer) let backToIntMax = intMaxData.integer // 9223372036854775807
let myInt32Data = Int32(1_234_567_890).data // 4 bytes (32 bit Integer) let backToInt32 = myInt32Data.int32 // 1234567890 let int32MinData = Int32.min.data // 4 bytes (32 bit Integer) let backToInt32Min = int32MinData.int32 // -2147483648 let int32MaxData = Int32.max.data // 4 bytes (32 bit Integer) let backToInt32Max = int32MaxData.int32 // 2147483647
let myFloatData = Float.pi.data // 4 bytes (32 bit single=precison FloatingPoint) let backToFloat = myFloatData.float // 3.141593 backToFloat == .pi // true let myDoubleData = Double.pi.data // 8 bytes (64 bit double-precision FloatingPoint) let backTodouble = myDoubleData.double // 3.141592653589793 backTodouble == .pi // true let myFloat80Data = Float80.pi.data // 16 bytes (128 bit extended-precision FloatingPoint) let backToFloat80 = myFloat80Data.float80 // 3.141592653589793116 backToFloat80 == .pi // true
let myStringData = Data("Hello World !!!".data.prefix(4)) // 4 bytes let backToString = myStringData.string // "Hell"