位缓冲区在 C 中的行为不符合预期

问题描述 投票:0回答:1

我必须将各个位写入文件(对于霍夫曼代码)。为此,我将位发送到一个函数,该函数对它们进行缓冲,直到填充一个字节,然后返回该字节。我不明白为什么它不起作用,该函数输出错误的字节(但没有错误)。 这是bitsBuffer函数:

// Buffers bits until one byte is filled, the returns it and return code turns positive
int bitsBuffer(char inByte, char nBits, char* outByte, char finish)
{
    int i;
    static short unsigned buffer = 0;
    static char unsigned offset = 0;

    // Very readable way to add nBits Bits to buffer
    buffer |= (inByte & ~(~0 << nBits)) << offset;
    offset += nBits;
    if (offset >= 8) {
        *outByte = (char)buffer;
        buffer >>= 8;
        offset -= 8;
        return 1;
    }
    if (finish) {
        buffer = 0;
        if (offset) {
            *outByte = (char)buffer;
            offset = 0;
            return 1;
        }
        offset = 0;
        return 0;
    }
    return 0;
}

我使用这个程序来测试位缓冲区,然后将输出通过管道传输到

xxd -b
以查看位:

#include "bitsHandler.h"
#include <stdio.h>

int main()
{
    char a[] = { 0b0110, 0b1, 0b100010, 0b111, 0b100110, 0b0 };
    char b[] = { 4, 1, 6, 3, 6, 1 };
    char c[100];
    int counter = 0;
    for (int i = 0; i < 6; i++) {
        if (bitsBuffer(a[i], b[i], &c[counter], 0)) {
            counter++;
        }
    }
    if (bitsBuffer(0, 0, &c[counter], 1)) {
        counter++;
    }
    fwrite(c, sizeof(char), counter, stdout);
}

我在纸上复制了该函数(手动完成了每一步),但我找不到我的错误。感谢帮助。

c bit-manipulation huffman-code binary-operators
1个回答
0
投票

除了您的位顺序有点奇怪(因为您将新位添加到缓冲区顶部并将它们从底部取出)这一事实之外,您在

finish
路径中还有一个错误。

    if (finish) { 
        buffer = 0; // <<<==== This is a bug I think
        if (offset) {
            *outByte = (char)buffer;
            offset = 0;
            return 1;
        }
        offset = 0;
        return 0;
    }

当我干运行你的测试数据时,当你的代码到达标记为“我认为这是一个错误”的行时,

buffer
仍然有一些位。即
0b01001
offset
是5。最后五个位永远不会被写入输出。

© www.soinside.com 2019 - 2024. All rights reserved.