C:计算跨越几个字节的一系列位

时间:2013-08-22 13:02:49

标签: c bit-manipulation

我有一个unsigned char字节数组,如:

unsigned char[20] = {0xff, 0x1a, 0x70, 0xa9, ...}

我现在想要对这个数组的x个连续位执行计算(使用x > 8;例如x = 15)。特别是,我希望每15位执行一次majortiy投票,返回一位。随后,返回的单个位将再次转换为无符号字节。

我已经实现了dominVoting算法。我还为整个问题实现了一个简单的算法,它以这种方式工作:

  1. 将字节数组转换为位数组(也是保存零和1的unsigned char [])
  2. 循环位数组并将每一系列x位传递给多数表决函数
  3. 也会在位数组(unsigned char [])
  4. 中收集多数投票结果
  5. 遍历此位数组并使用按位运算从每个8位系列构造字节。
  6. 对我而言,这似乎很直观,但同时也很麻烦。

    您是否看到了优化的可能性,或者您甚至可以提供更流畅的算法?

    祝你好运, P上。

2 个答案:

答案 0 :(得分:0)

您可以使用类似

的函数获取数组的下一位
 int nextBit( unsigned char [] arr, int *pByte, size_t nBytes, int *pBit ) 
 {
      int result;

      if( *pByte >= nBytes ) {
          // Padding, neccessary if nBytes % 15 != 0
          return 0;
      } else {
          result = ( arr[*pByte] >> (*pBit) ) & 0x1;
          if( *pBit == 7 ) {
              (*pByte)++;
              *pBit = 0;
          } else {
              (*pBit)++;
          }
          return result;
      }
 }

和循环:

 int byte=0, bit=0;
 int result;
 int i;

 while( byte < sizeof( arr ) ) {
     for( i=0; i<15; i++ ) {
         result = nextBit( arr, &byte, sizeof( arr ), &bit );
         // do the majority voting
     }
 }

可以创建一个非常相似的函数来直接创建多数位数组

答案 1 :(得分:0)

您可以将每个字节移位到17位(并将它们存储在17个字节中)。

uint8_t bits[17];
bits[0] = !!(bytes[0] & 128);
bits[1] = !!(bytes[0] & 64);
bits[2] = !!(bytes[0] & 32);
bits[3] = !!(bytes[0] & 16);
bits[4] = !!(bytes[0] & 8);
bits[5] = !!(bytes[0] & 4);
bits[6] = !!(bytes[0] & 2);
bits[7] = !!(bytes[0] & 1);
bits[8] = !!(bytes[1] & 128);
bits[9] = !!(bytes[1] & 64);
bits[10] = !!(bytes[1] & 32);
bits[11] = !!(bytes[1] & 16);
bits[12] = !!(bytes[1] & 8);
bits[13] = !!(bytes[1] & 4);
bits[14] = !!(bytes[1] & 2);
bits[15] = !!(bytes[1] & 1);
bits[16] = !!(bytes[2] & 128);

我不确定你想用这些位做什么,但你也可以考虑将这些位存储在32位整数中:

uint32_t chunk = (bytes[0] << 9) | (bytes[1] << 1) | (bytes[2] & 1);