写入 boost::d ynamic_bitset 到文件

Write boost::dynamic_bitset to file

本文关键字:bitset 文件 ynamic boost 写入      更新时间:2023-10-16

我正在实现香农-法诺编码算法,我想将符号代码输出为位。

例如,在下面的代码中,我逐行从输入文件(fin流)中读取符号,用算法形成的符号代码(来自std::map<unsigned short, std::string> symbolCodes)填充std::string,然后用currentOutString的内容构造boost::dynamic_bitset。然后我尝试输出位集,但在输出文件中,位集中的每个"真"或"假"值占用 1 个字节而不是 1 位。

if (fin.is_open() && fout.is_open()) {
    std::string currentInString;
    std::string currentOutString;
    while (getline(fin, currentInString)) {
        boost::dynamic_bitset<> bitSet;
        for (auto & ref : currentInString) {
            currentOutString += symbolCodes[ref];
        }
        for (auto & ref : currentOutString) {
            if (ref == '0') bitSet.push_back(0);
            if (ref == '1') bitSet.push_back(1);
        }
        fout << bitSet;
        bitSet.clear();
        currentOutString.erase();
    }
}

fout流以std::ios_base::binary模式打开。例如,我有单词"文件",代码e: 00, f: 01, i: 10, l: 11。如何输出我的位集,所以输出文件占用 8 位而不是 8 字节?

提前感谢您的帮助,对于可能的语言错误,深表歉意。

这实际上不是dynamic_bitset的错,而是iostream的错。

打印以下代码

123----.

cout

#include <iostream>
#include <boost/dynamic_bitset.hpp>
int main() {
    using namespace std;
    using namespace boost;
    auto bitset = dynamic_bitset<>(32, 0x0a333231); // "123n" in little endian
    bitset.append(0x2d2d2d2d); // "----"
    bitset.append(0x0a2e); // ".n"
    // bitset.size() is at least 96 here
    auto ulong_mask = dynamic_bitset<>(bitset.size(), 0xFFFFFFFFul);
    while(bitset.any()) {
        unsigned long ulong = (bitset & ulong_mask).to_ulong();
        cout.write(reinterpret_cast<char*>(&ulong), sizeof(ulong));
        bitset >>= 32;
    }
}

请注意使用 cout.write() 而不是 operator << 。它按原样输出字节,没有任何格式和转换为 ASCII 字符串(想想itoa()或类似的东西)。


还有一点:由于dynamic_bitset不提供连续的存储保证和/或访问,我们必须按块读出大比特集,最好是更大的比特集;例如 unsigned long .

在某些架构上,sizeof(unsigned long)将是 8,所以我们实际上可以使用更大的ulong_maskULONG_MAX可以),并相应地移动 (8 * sizeof(unsigned long))。使用它。(为便于说明,上文第32段为硬编码)。