1

I have designed a custom file format / network message to reduce size as much as possible, but I don't know how to implement it. Any heads up will be helpful.

The first 2 bytes, correspond to 2 numbers, ranging from 0 to 63, so I'm using 6 bits. In the remaining 4 bits, I store another number, from 0 to 15.

So for example, if I have numbers 34, 25 and 15, the bits would look like:

34---|25----|15--
10001001 10011111

I looked over BitArray, and BitConverter, but I found functions to work on 8-bit, 16-bit and 32-bit types, not on custom ones.

Of course the complete format is much longer, but if I understand this I think I'll be able to continue.

Anyone have some advice or can give me a hint to start this?

Thanks!

Jorjon
  • 5,316
  • 1
  • 41
  • 58
  • 1
    Just because I'm interested - whats the application? What size are the buffers (what kind of saving do you see)? – Kieren Johnstone Oct 19 '11 at 17:35
  • What's your point? In the example, you're still sending 16 bits across the wire; how does it help whether you say "this is 8+8 bits" or "this is 6+6+4 bits"? Am I missing something? – Piskvor left the building Oct 19 '11 at 17:39
  • In your example, the first number sent is actually 35. – dlev Oct 19 '11 at 17:44
  • 1
    http://stackoverflow.com/questions/3882780/mapping-c-data-structures-and-typedefs-to-net/6234062#6234062 might be of interest – Greg Buehler Oct 19 '11 at 17:49
  • @Veehmot - You do understand that sending 0x000005 vs sending 0x5 is going to send the same value correct? **BitConverter** is exactly what you want to use. – Security Hound Oct 19 '11 at 17:50
  • The advantage of this, is that usually for 3 numbers I would send 3 bytes, one for 34, one for 25 and one for 15. With this, I can only send 2 bytes, given that the numbers fall within the specified range. – Jorjon Oct 19 '11 at 18:39
  • @KierenJohnstone: the application is a lo-fi game, using Unity3D engine. – Jorjon Oct 19 '11 at 18:42

2 Answers2

2

I am afraid you have to write your bit manipulation code yourself. In your example, the code would look something like this:

int a = 34;
int b = 25;
int c = 15;

byte[] data = new byte[2];

// Store to byte array
data[0] = (byte)((a << 2) + (b >> 4));
data[1] = (byte)((b << 4) + c);

// Read from byte array
a = data[0] >> 2;
b = ((data[0] & 3) << 4) + (data[1] >> 4);
c = data[1] & 15;

Console.WriteLine("a = " + a); // 34
Console.WriteLine("b = " + b); // 25
Console.WriteLine("c = " + c); // 15

You can use the bit shift operators (<< and >>) and the logical bit operators (| and &) to manipulate the bits.

Elian Ebbing
  • 18,779
  • 5
  • 48
  • 56
  • Now this was useful! I guess I should make all the accessors by hand, but good thing is that this can be ported on all languages that support bitwise operations. I complemented your answer with the display of each operation: http://pastebin.com/dp9NvsqJ – Jorjon Oct 19 '11 at 19:41
  • 1
    Oh an sorry to correct you, but instead `data[1] & 31` it would be `data[1] & 15`. – Jorjon Oct 20 '11 at 08:26
1

I looked over BitArray, and BitConverter, but I found functions to work on 8-bit, 16-bit and 32-bit types, not on custom ones.

You will have to write your own functions. I would simply advise a structure instead. You can then send X Bytes, read and parse those Bytes into your structure, and not have to worry about writting your own methods.

This is how you would normally do it. You can define the exact size of the structure and it would work exactly like you want it to.

Security Hound
  • 2,577
  • 3
  • 25
  • 42