从字节数组中读取位范围

时间:2012-09-26 19:11:53

标签: c# byte bit-manipulation bit

我正在寻找一种能让我得到一系列位的方法。例如,如果我有二进制数据

0 1 0 1 1 0 1 1 1 1 0 1 0 1 1 1 (2个字节)

我可能需要从第3位到第9位获取数据。换句话说,我会感兴趣:

0 1 0 1 1 0 1 1 1 1 0 1 0 1 1 1

所以总之我想构建方法:

 byte[] Read(byte[] data, int left, int right){ 

     // implementation
 }

因此,如果我传递数据new byte[]{91,215}, 3, 9,我将获得byte[]{122}(注意字节91和215 = 0 1 0 1 1 0 1 1 1 1 0 1 0 1 1 1和字节122 = 1 1 1 1 0 1 0相同的二进制数据

如果我可以在字节数组上使用<<运算符,例如执行以下操作,那就太好了。

  byte[] myArray = new byte[] { 1, 2, 3 };
  var shift = myArray << 2;

如果您有兴趣知道我为什么需要此功能:

我在电路板上创建一个项目,经常需要读取和写入内存值。 cdf,sfr或ddf(称为芯片定义文件)包含有关特定芯片的信息。该文件可能如下所示:

;     Name                            Zone      Address     Bytesize  Displaybase Bitrange
;     ----                            ----      -------     --------  ----------- --------

sfr = "SPI0_CONTROL"              , "Memory", 0x40001000,        4, base=16
sfr = "SPI0_CONTROL.SPH"          , "Memory", 0x40001000,        4, base=16,    bitRange=25-25
sfr = "SPI0_CONTROL.SPO"          , "Memory", 0x40001000,        4, base=16,    bitRange=24-24
sfr = "SPI0_CONTROL.TXRXDFCOUNT"  , "Memory", 0x40001000,        4, base=16,    bitRange=8-23
sfr = "SPI0_CONTROL.INT_TXUR"     , "Memory", 0x40001000,        4, base=16,    bitRange=7-7
sfr = "SPI0_CONTROL.INT_RXOVF"    , "Memory", 0x40001000,        4, base=16,    bitRange=6-6

由于我正在阅读很多变量(有时每秒80次),我希望有一个有效的算法。我想我的方法是,如果bytesize为8,那么我将从这8个字节创建一个long,然后使用<<>>运算符来获得我需要的东西。如果bytesize if 4那么我将创建一个int并使用<<>>运算符但是如果我需要读取16个字节,我该怎么办呢? 我想我的问题应该是如何在自定义结构类型上实现<<>>运算符。

3 个答案:

答案 0 :(得分:5)

您需要 System.Collections 中的BitArray课程。

答案 1 :(得分:3)

看起来你可以帮助“比特流”。有一个这样的概念here的实现。看看,也许它符合您的需求。

答案 2 :(得分:2)

.NET 4+中的BigInteger类在其构造函数中使用Byte[]并且具有左移和右移运算符。