2009-08-14 45 views
1

你好,快速关于移位的问题移位N位

我有一个HEX = new byte [] {0x56,0xAF}的值;

其是0101 0110 1010 1111

我想第一n位,例如12

然后推卸其余4(16-12),以获得0000 0101 0110 1010(1386分解)

我无法用头围住它,并使其可扩展n位。

谢谢!

回答

1

你想要的东西像...

var HEX = new byte[] {0x56, 0xAF}; 
var bits = new BitArray(HEX); 
int bitstoShiftRight = 4; 
for (int i = 0; i < bits.Length; i++) 
{ 
    bits[i] = i < (bits.Length - bitstoShiftRight) ? bits[i + bitstoShiftRight] : false; 
} 
bits.CopyTo(HEX, 0); 
+0

谢谢,我喜欢这种方法,问题是BitArray的构造函数改变了每个字节的Endian的顺序,当方法完成后,值出错,id需要在实例化位数组之前反转每个字节的位顺序byes – Bobby 2009-08-14 16:06:09

0

如果你有全部K位,你想要的“第一”(如最显著)n位,则您只需右键转变时间。最后的k-n位将被删除,通过结尾的“下降”,第一个n将移动到最不重要的一侧。

+0

感谢您的回应,问题是我真的不能移位一个字节数组,我需要单独做它们,然后我失去了溢出,所以我的替代方案是将整个16位转换为int 16和shift在那个时候,没有我想要的东西,因为我现在需要知道长度,然后转换为 – Bobby 2009-08-14 16:03:34

0

用C状符号应答,假定bits_in_byte是别处确定的比特的字节数:

int remove_bits_count= HEX.count*bits_in_byte - bits_to_keep; 
int remove_bits_in_byte_count= remove_bits_count % bits_in_byte; 

if (remove_bits_count > 0) 
{ 
    for (int iteration= 0; iteration<min(HEX.count, (bits_to_keep + bits_in_byte - 1)/bits_in_byte); ++iteration) 
    { 
     int write_index= HEX.count - iteration - 1; 
     int read_index_lo= write_index - remove_bits_count/bits_in_byte; 

     if (read_index_lo>=0) 
     { 
      int read_index_hi= read_index_lo - (remove_bits_count + bits_in_byte - 1)/bits_in_byte; 

      HEX[write_index]= 
       (HEX[read_index_lo] >> remove_bits_in_byte_count) | 
       (HEX[read_index_hi] << (bits_in_byte - remove_bits_in_byte_count)); 
     } 
     else 
     { 
      HEX[write_index]= 0; 
     } 
    } 
} 

假设你重写原数组,则基本上采取每次写入字节,并计算出它将从其获得其移位的字节。你从数组的最后到最前面确保你永远不会覆盖你需要阅读的数据。

6

早前我编码这两个功能,第一个移位位的字节[]指定的量的左侧,第二做同样向右:

左移:

public byte[] ShiftLeft(byte[] value, int bitcount) 
{ 
    byte[] temp = new byte[value.Length]; 
    if (bitcount >= 8) 
    { 
     Array.Copy(value, bitcount/8, temp, 0, temp.Length - (bitcount/8)); 
    } 
    else 
    { 
     Array.Copy(value, temp, temp.Length); 
    } 
    if (bitcount % 8 != 0) 
    { 
     for (int i = 0; i < temp.Length; i++) 
     { 
      temp[i] <<= bitcount % 8; 
      if (i < temp.Length - 1) 
      { 
       temp[i] |= (byte)(temp[i + 1] >> 8 - bitcount % 8); 
      } 
     } 
    } 
    return temp; 
} 

右移:

public byte[] ShiftRight(byte[] value, int bitcount) 
{ 
    byte[] temp = new byte[value.Length]; 
    if (bitcount >= 8) 
    { 
     Array.Copy(value, 0, temp, bitcount/8, temp.Length - (bitcount/8)); 
    } 
    else 
    { 
     Array.Copy(value, temp, temp.Length); 
    } 
    if (bitcount % 8 != 0) 
    { 
     for (int i = temp.Length - 1; i >= 0; i--) 
     { 
      temp[i] >>= bitcount % 8; 
      if (i > 0) 
      { 
       temp[i] |= (byte)(temp[i - 1] << 8 - bitcount % 8); 
      } 
     } 
    } 
    return temp; 
} 

如果您需要进一步的解释,请对此进行评论,我会再编辑自己的帖子澄清...

+0

预先复制8位移位溢出不是一个坏主意。我看到这个想法之前,我的实现有2个嵌套for-s来处理溢出。 – vellotis 2012-11-13 13:07:43