gpt4 book ai didi

c - 位读取器在连续非 8 倍数读取时失败

转载 作者:行者123 更新时间:2023-11-30 15:13:59 25 4
gpt4 key购买 nike

过去两天我一直在努力解决这个问题,目前我可能已经修复了至少 20 个不同的错误。

基本上,这个错误是如果你调用 ReadBits() 并请求任何不是 8 的倍数的内容,它第一次会工作,但如果你再次调用它,使用另一个非 8 的倍数,它就不会工作.

我第一次使用 61 位,第二次使用 33 位,仅作为示例。

这是请求 61 位的输出:0x1FFFFFFFFFFFFFFF从 33 开始:0x1FFFFFFF8

33位输出中的最后一个字节应该是FF,但由于某种原因它是F8?如果我将它移到 3 个空位上,它的长度就只有 30 位,而不是应有的 33 位。

struct BitIO {
FILE *InputFP;
fpos_t *InputOffset;
uint64_t InputFPSize;
uint8_t InputBuffer[BufferSizeInBytes];
uint64_t InputBitIndex;
} BitIO;

static const uint8_t ByteMask[2][8] = {
{0xFF, 0x7F, 0x3F, 0x1F, 0x0F, 0x07, 0x03, 0x01},
{0xFF, 0x80, 0xC0, 0xE0, 0xF0, 0xF8, 0xFC, 0xFE}
};

static const uint8_t ShiftTable[8] = {
0, 7, 6, 5, 4, 3, 2, 1
};


uint64_t Bits2Bytes(uint64_t Bits) {
return (Bits + 7) >> 3;
};

uint64_t ReadBits(int8_t Bits2Read) {
uint64_t OutputData = 0;

uint64_t StartByte = Bits2Bytes(BitIO.InputBitIndex - (BitIO.InputBitIndex % 8));
uint64_t EndByte = Bits2Bytes((BitIO.InputBitIndex + Bits2Read));
uint64_t BufferShift = ShiftTable[BitIO.InputBitIndex % 8];
uint64_t Bits2ReadShift = ShiftTable[Bits2Read % 8];
uint64_t ByteMaskStart = ByteMask[0][~(BitIO.InputBitIndex % 8)];

for (uint64_t Byte = StartByte; Byte < EndByte; Byte++) {
if (EndByte == StartByte + 1) {
OutputData += BitIO.InputBuffer[Byte] & ByteMask[1][(BitIO.InputBitIndex + Bits2Read) % 8];
OutputData >>= ShiftTable[(BitIO.InputBitIndex + Bits2Read) % 8];
} else if (Byte == StartByte) {
OutputData += BitIO.InputBuffer[Byte] & ByteMask[1][Bits2Read % 8];
OutputData >>= Bits2ReadShift;
OutputData <<= 8;
} else if (Byte == EndByte - 1) {
OutputData += BitIO.InputBuffer[Byte] & ByteMask[1][(BitIO.InputBitIndex % 8)];
} else if (Byte != StartByte && Byte != EndByte) {
OutputData += BitIO.InputBuffer[Byte];
OutputData <<= 8;
}
}
BitIO.InputBitIndex += Bits2Read;
return OutputData;
};

最佳答案

试试这个:

static const uint8_t ByteMask[2][8] = {
{0xFF, 0x7F, 0x3F, 0x1F, 0x0F, 0x07, 0x03, 0x01},
{0x00, 0x80, 0xC0, 0xE0, 0xF0, 0xF8, 0xFC, 0xFE}
};

第一个条目是错误的,尽管下面的条目不使用它。

// assume 0 <= n <= 64
uint64_t ReadBits (int n)
{
uint64_t r = 0;
uint64_t byte = BitIO.InputBitIndex / 8;
uint64_t bit = BitIO.InputBitIndex % 8;
while (n > 0) {
int count = (n >= 8) ? 8 : n;
n -= count;
uint64_t tmp;
// We make sure not to look at two bytes if we don't have to
// to avoid a buffer overrun.
if (bit == 0) {
tmp = BitIO.InputBuffer[byte];
}
else {
uint64_t x = BitIO.InputBuffer[byte] & ByteMask[0][bit];
uint64_t y = BitIO.InputBuffer[byte + 1] & ByteMask[1][bit];
tmp = ((x << 8) | y) >> (8 - bit);
}
tmp >>= (8 - count);
BitIO.InputBitIndex += count;
byte++;
r = (r << count) | tmp;
}
return r;
}

关于c - 位读取器在连续非 8 倍数读取时失败,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34233656/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com