1

So I'm trying to write a function that will convert a 7-bit Gray code to the corresponding 7-bit Binary Code.

Here's how to convert -

  • Gray Value bits ---- MS bit > (G6) G5 G4 G3 G2 G1 G0 *
  • Binary Value bits -- MS bit > (B6) B5 B4 B3 B2 B1 B0 *

  • B6 = G6 // MS bits always the same

  • B5 = B6 ^ G5 // Exclusive 'OR' the bits together to construct the 7 bit binary value
  • B4 = B5 ^ G4
  • B3 = B4 ^ G3
  • B2 = B3 ^ G2
  • B1 = B2 ^ G1
  • B0 = B1 ^ G0

and here's my function so far-

unsigned short Gray_to_Bin(unsigned short Gray)
{
unsigned short Bin;
unsigned short i;
unsigned short mask;

mask = 0x40; // Initial mask
Bin = 0;

Gray &= 0x7f; // Mask bit 7 (Index Bit)
Bin = Gray & mask; // Set B6 = G6

for (i=0; i<6; i++) // Set B5, B4, ..., B0
{

// Code needed here!!

}
return Bin;
}

I need to find a way to access the required specific bits for each run of the loop...need to access the bits like I could with arrays somehow...

Any ideas/pointers? Thanks :)

S_Wheelan
  • 267
  • 2
  • 5
  • 8

7 Answers7

3

A more optimized code to convert gray to binay will be

int grayToBinary(int gray)
{
int binary=0;
for(;gray;gray=gray>>1)
{
    binary^=gray; //binary=binary^gray;
}
return binary;
}

This technique uses bit wise operator.

2

The following implements the bitwise assembly of the result following the requirement you gave..

  • B6 = G6 // MS bits always the same
  • B5 = B6 ^ G5
  • ...

For B5, I simply bitshift the B6 value right one bit so it corresponds with the grey bit G5, XOR them then filter away the other bits with an & operation. These bitwise results are ORed to create the overall result. Repeat for successive bits. It's not even worth having a loop for this... just extra possible runtime overhead, and source code complexity.

unsigned short gray_to_binary(unsigned short gray)
{
    unsigned short result = gray & 64;
    result |= (gray ^ (result >> 1)) & 32;
    result |= (gray ^ (result >> 1)) & 16;
    result |= (gray ^ (result >> 1)) & 8;
    result |= (gray ^ (result >> 1)) & 4;
    result |= (gray ^ (result >> 1)) & 2;
    result |= (gray ^ (result >> 1)) & 1;
    return result;
}
Tony Delroy
  • 102,968
  • 15
  • 177
  • 252
1

The fastest way I know to translate gray code to binary code implements this Java method:

private static int grayToBin(int gray) {
   int bin = 0;
   while (gray != 0) {
      int decremented = gray - 1;
      bin ^= gray;
      bin ^= decremented;
      gray &= decremented;
   }
   return bin;
}
korsak
  • 11
  • 1
0

what is the problem with just what you wrote in your question i mean in you for statement you can write B[i] = B[i+1]^G[i]; you just have to change your for so it goes from 4 downto zero

Ali1S232
  • 3,373
  • 2
  • 27
  • 46
  • Well, the codes aren't in array form - the gray codes coming in would be like 0101 1100. I didn't think you could access each digit of a short like you could in an array? ( Excuse my ignorance, I'm new to this :P ). Thanks! – S_Wheelan Mar 15 '11 at 08:17
0

The following code should do the trick:

for (int i = 0; i < 6; ++ i) {
    unsigned short j = 5 - i;
    unsigned short m = 1 << j;
    Bin |= ((Bin >> 1) & m) ^ (Gray & m);
}
Sylvain Defresne
  • 42,429
  • 12
  • 75
  • 85
0

I think it should look something like this:

for(i=5; i >= 0; i--){
    Bin = Bin | ((Gray & 1<<i)>>i ^ (Bin & 1<<(i + 1))>>i)<<i;
}

To access a particular bit, you use 1<<i to left shift "1" i times, producing a number that is all zeroes except a one in the ith place from right. This can be ANDed with Gray or Bin, zeroing all bits except the one we care about. The result is then right-shifted using >>i, moving the bit we care about to the far right. We use ^ to xor the two bits, then shift it left to where the resulting bit belongs and OR it ints Bin.

This gives a very useful explanation.

0

For just about any conversion of one seven bit code to another, the simplest solution is just a table, e.g.: static unsigned char fromGray[] = { 0x00, 0x01, 0x03, 0x02, 0x06, 0x07, 0x05, 0x04, 0x0C, 0x0D, 0x0F, 0x0E, 0x0A, 0x0B, 0x09, 0x08, 0x18, 0x18, 0x1B, 0x1A, 0x1E, 0x1F, 0x1D, 0x1C, 0x14, 0x15, 0x17, 0x16, 0x12, 0x13, 0x11, 0x10, // .... };

At some point between 8 and 16 bits, you'll probably want to shift to an algorithmic approach (although given the memory available on modern processors, the table approach is valid for pretty big tables). Even then, I'd probably use the table for the low order bits.

James Kanze
  • 150,581
  • 18
  • 184
  • 329