如何从Swift中的Big endian表示计算Int值



我正在通过BLE传输UInt16值。根据我所读到的内容,为此,我需要将UInt16转换为UInt8,后者将转换为类型Data。我一直在提到这个话题。例如,我使用了以下代码:

extension Numeric {
var data: Data {
var source = self
return Data(bytes: &source, count: MemoryLayout<Self>.size)
}
}
extension Data {
var array: [UInt8] { return Array(self) }
}
let arr = [16, 32, 80, 160, 288, 400, 800, 1600, 3200]
for x in arr {
let lenghtByte = UInt16(x)
let bytePtr = lenghtByte.bigEndian.data.array
print(lenghtByte, ":", bytePtr)
}

我不太明白的是,当我将UInt16转换为大端数组时,这些值将如何相加到相应的实际值。希望这是有道理的。上面片段的输出是,

16 : [0, 16]
32 : [0, 32]
80 : [0, 80]
160 : [0, 160]
288 : [1, 32]
400 : [1, 144]
800 : [3, 32]
1600 : [6, 64]
3200 : [12, 128]

我想知道的是,如何使用Big endian数组中的UInt8值来计算160之后的每个值?(即[12128]如何等同于3200)。

提前感谢:)

data属性的作用是查看数字的二进制表示,将其分割为字节,并将其放入Data缓冲区。例如,对于big-endian中的1600,二进制表示如下所示:

0000011001000000

注意,整数中有两个字节——00000110(十进制的"6")和01000000(十进制的"64")。这就是[6, 64]的来源。

要从[6, 64]获得1600,您只需要意识到";6〃;实际上并不代表6;5〃;在52中不代表5,而是5*10。在这里;6〃;表示6 * 2566 << 8(向左移动6次)。总的来说,要想拿回号码,你需要进行

a << 8 + b

其中a是第一阵列元素,而b是第二阵列元素。

一般来说,对于一个有n个字节的数字,你可以这样计算:

// this code is just to show you how the array and the number relates mathematically
// if you want to convert the array to the number in code, see
// https://stackoverflow.com/a/38024025/5133585
var total = 0
for (i, elem) in byteArray.enumerated() {
total += Int(elem) << (8 * (byteArray.count - i - 1))
}

最新更新