2

我有一个长度为 5 位的值。4 位决定数字,第 5 位决定符号,保持 -16 和 +15 之间的任何值。如何在 C# 中完成从恒定位宽扩展的符号?我知道在 C 中,我可以使用类似以下的内容来完成此操作:

int x; // convert this from using 5 bits to a full int
int r; // resulting sign extended number goes here
struct {signed int x:5;} s;
r = s.x = x;

我怎样才能在 C# 中做类似的事情?

4

5 回答 5

3

你的意思不是很清楚,但它可能很简单:

int fiveBits = normal & 0x1f;

反过来:

int normal =  fiveBits < 16 ? fiveBits : fiveBits | -32;

如果您可以建议一些原始输入和所需的输出,那将有所帮助。

于 2010-10-20T18:38:22.383 回答
2

我只是在编写一个 C 函数(因为我并不真正了解 C#),它将使用我知道在 C# 中可用的操作来执行此操作。

int five_bit_to_signed(int five_bit) {
     int sh = (sizeof(int)*8)-5;
     int x = five_bit << sh; // puts your sign bit in the highest bit.
     return x >> sh;  // since x is signed this is an arithmatic signed shift
}
于 2010-10-20T19:25:23.383 回答
2

我知道这是一个老问题,但对于未来的搜索者,我有更多信息。

C# 不支持自定义位宽,但它支持二进制操作和 getter/setter,这使得添加兼容层相对容易。例如,如果您想将原始数据存储在字节 _num 中,但希望能够使用标准 C# sbyte 与其交互,您可以使用以下内容:

byte _num;
sbyte num {
    get
    {
        return (sbyte)(((_num & 0x10) << 3) | (_num & 0x0F));
    }
    set
    {
        _num = (byte)((value & 0x0F) | ((value & 0x80) >> 3));
    }
}

这种外壳在与低级固件或嵌入式项目交互时特别有用。

于 2012-06-06T15:14:33.350 回答
1

执行左移,然后执行算术右移,将符号位移到高位,然后返回。算术右移将为您执行符号扩展。

当然,这取决于有一个有效的算术移位操作。抽象的 C 语言没有(它是否工作由实现定义),但大多数实现都可以。我不确定C#,但我猜它有一个。

于 2010-10-20T19:07:37.337 回答
0

从您的问题来看,您似乎希望拥有一个可以轻松转换为int类型的结构:

struct FiveBit
{
  public int bits;

  public static implicit operator int(FiveBit f)
  {
    return (f.bits & 0x10) == 0 ? f.bits : f.bits | -32;
  }

  public static implicit operator FiveBit(int r)
  {
    return new FiveBit() { bits = r & 0x1f };
  }
}

这是一个使用示例:

class FiveBitTest
{
  static void Main(string[] args)
  {
    FiveBit f = new FiveBit();
    int r; // resulting sign extended number goes here

    f.bits = 0;
    r = f;
    Console.WriteLine("r = {0}, f.bits = 0x{1:X}", r, f.bits);

    f.bits = 0x1f;
    r = f;
    Console.WriteLine("r = {0}, f.bits = 0x{1:X}", r, f.bits);

    r = -2;
    f = r;
    Console.WriteLine("r = {0}, f.bits = 0x{1:X}", r, f.bits);
}

上面的输出是:

r = 0, f.bits = 0x0
r = -1, f.bits = 0x1F
r = -2, f.bits = 0x1E
于 2012-03-29T08:41:21.163 回答