Working with Bits & Bytes
To send data back and forth over a LoRaWAN network, you'll need to know how to use bits and bytes. Because the packet size is very limited with LoRaWAN (around 200 bytes with a high data rate, and about 50 bytes with a low data rate), you must be very clever about the kind of data you send.
What is a byte?
A byte is a group of eight bits. A bit is the most basic unit of data, and can be either 1 or 0. A byte is not just eight values between 0 and 1, but 256 (28) different values, ranging from 00000000 to 11111111 in binary. Given these combinations, each byte can represent a decimal number between 0(00) and 255.
Puzzled? Remember that three decimal numbers don’t just stand for three values between 0 and 9, but 1000 (103) permutations from 0 to 999.
Learn more at How Bits and Bytes Work and in the Arduino playground: BitMath Tutorial.What is a Buffer of Bytes?
Think of a buffer as just another word for an array or list. Where a byte is a group of eight bits, a buffer is a group of a predefined number of bytes. If we have a group of three bytes, this could represent either three values between 0 and 255 or a single value between 0 and 16777216 (2563).
See the pattern? The number of choices per position (n) to the power of the number of positions (r) is the number of permutations: nr. Learn more on MathIsFun.com.
What is Hex?
Often, you'll see a group of bytes displayed as:
Wasn’t a byte a group of eight 0s and 1s?
Exactly right. However, as we saw, we can translate the byte 11111111 to 255 in the good old decimal system, we can also translate it to FF F0 0F 11 in the hexadecimal
system, where each position has
16 possible values (0-9 and A-F). The advantage of hex is that it is shorter
and more explicit about the maximum value (for example, 257 is not an option).
If we translate FF F0 0F 11 to the decimal system and pad for readability, we get
To indicate that you mean 11 in hex and not two bits or the number eleven, you prefix it with the 0x formatter. To tell it you mean binary use B, as indicated in the following table.
Code | Byte Value | Decimal Value | Hexadecimal (Hex) Value |
---|---|---|---|
11 | 00001011 | 11 | B |
0x11 | 00010001 | 17 | 11 |
B11 | 00000011 | 3 | 3 |
Let’s look at one more example:
byte data[] = { 0xFF, 0xF0, 0x0F, 0x11 };
// identical: { 255, 240, 15, 17 };
// identical: { B11111111, B11110000, B00001111, B00010001 };
ttn.sendBytes(data, sizeof(data));
Using 0x not only means that it is shorter to write than a decimal, it's also a lot easier to convert the number into binary. Hence, it is a good option much of the time.