1
我开始创建iOS应用程序以通过BLE与设备进行通信的项目。作为一个新的努力,我想尽可能做到这一点是Swift。该接口使用GATT和一组现有的消息结构。我得到了一个点,在这个点我有来自BLE的数据,在NSData
对象中。我想转换它,或者直接将它转换为我的消息结构。将NSData字节转换为自定义对象
我知道我可以直接从NSData
对象的字节数组中手动提取数据,或者使用NSInputStream
。虽然这有效,但它可能是一个维护问题,并且界面中有许多不同的消息。
有没有更简单的方法来做到这一点?我会愿意在Objective-C中创建消息结构并在那里进行投射,但是我对Objective-C的了解并不比我对Swift的了解好很多。
下面显示了我在游乐场玩过的一些示例代码。这一切都按预期工作。
func getBytesFromNSData(data: NSData, start: Int) -> [UInt8] {
let count = data.length/sizeof(UInt8)
let remaining = count - start
let range = NSMakeRange(start, remaining)
var dataArray = [UInt8](count: remaining, repeatedValue: 0)
data.getBytes(&dataArray, range: range)
return dataArray
}
class TestObject {
var a: Byte
var b: Byte
init() {
a = 0x01
b = 0x02
}
init(data: NSData) {
let dataBytes = getBytesFromNSData(data, 0)
a = Byte(dataBytes[0])
b = Byte(dataBytes[1])
}
func populateFromStream(data: NSData) {
var stream = NSInputStream(data: data)
stream.open()
var bytesRead = stream.read(&a, maxLength: 1)
println("\(bytesRead)")
bytesRead = stream.read(&b, maxLength: 1)
println("\(bytesRead)")
}
func toArray() -> [Byte] {
var result = [Byte](count: 2, repeatedValue: 0)
result[0] = a
result[1] = b
return result
}
}
let test = TestObject()
let testArray = test.toArray()
let length = testArray.count
let testData = NSData(bytes: testArray, length: length)
println("\(testData)")
let testIn = [ Byte(0x0d), Byte(0x0e) ]
let testDataIn = NSData(bytes: testIn, length: testIn.count)
println("\(testDataIn)")
let testConstructor = TestObject(data: testDataIn)
var testObject = TestObject()
testObject.populateFromStream(testDataIn)
明白,几乎没有人知道GATT暗示什么样的数据结构。但是你显然想要做的那种反汇编最好在纯C中执行,或者通过定义'struct'来覆盖数据,或者通过读取单个字节并将其组装成所需的形式。 – 2014-11-05 12:18:49
这就是我要来的结论,但我希望有人可能会有不同的答案。读取单个字节在Swift中并不难,它只是单调乏味。 – 2014-11-05 12:40:31
最好的办法就是想出一个标准化的“风格”,用来处理所有事情,而不是特别的。例如,编写实用程序的方法,给你一个'int'或'double'或其他什么,从NSData对象的给定偏移量开始。然后编写那些移动到/从你的内部结构的序列。将复杂的偏移/长度计算保持在最小值,并将它们全部保留在一个点上。 – 2014-11-05 16:27:29