0

I am trying to open a file into an array of bits (0,1) in C++. Every example I have seen has been working with has bytes, but I really need the actual bits. Is there an easy way to do this? The file will be <100 kB.

11
  • 2
    std::bitset might help you. Commented May 15, 2013 at 21:57
  • You could use bitmasking to extract every bit from each byte you read. Commented May 15, 2013 at 21:59
  • @chris: Not really. He would still have to read a file byte by byte, and I don't see convenient conversion to bitset from there. Commented May 15, 2013 at 21:59
  • 1
    What's the difference? Bytes from string or bytes from file are still bytes. Just read them and accommodate them into bitset properly, as already provided in the link. Commented May 15, 2013 at 22:04
  • 1
    Some context would help here... bytes are made of bits, you have the bytes you have the bits, bits will be stored in bytes no matter what you try. If you want to get the bits mask the byte. Commented May 15, 2013 at 22:09

2 Answers 2

0

One of the problems with std::bitset is you have to template the size. You can just read it in manually though...

char c;
vector<char> bytes;
int nread = 0;

while( in.get(c) )
{
    if( nread == 0 ) bytes.push_back(0);
    bytes.back() = (bytes.back() << 1) | (c ? 1 : 0);
    nread = (nread + 1) % 8;
}
Sign up to request clarification or add additional context in comments.

1 Comment

On reflection, I may have misunderstood your intent. It seemed like you had a file of 0/1 values that you wanted to read into bits.
0
#include <bitset>
#include <sstream>
#include <iostream>
#include <cinttypes>

namespace my
{
    template<size_t S> 
    std::istream &operator >> (std::istream &is, std::bitset<S> &bits)
    {
        std::uint8_t byte;
        size_t i = 0;
        while(i < S && (is >> byte))
            for(size_t j = 0; j < 8 && i < S; ++j)
                bits[i++] = (byte >> j) & 1;
        return is;
    }
}

int main()
{

    constexpr size_t bytes = 2;
    std::string bit_string("\x00\xFF", bytes);
    std::istringstream bit_stream(bit_string);

    std::bitset<8 * bytes> b;

    {
        using namespace my;
        bit_stream >> b;
    }

    std::cout << b << std::endl;

    for(size_t i = 0; i < b.size(); ++i)
        std::cout << b[i];

    std::cout << std::endl;
}

output:

1111111100000000
0000000011111111

run live:

http://ideone.com/Is7xRy

notes:

  • bitset size is a non-type template parameter. You can't set it at runtime. So, this will only work with preallocation of the bitset and you'll get 0 padding for a larger bitset.
  • If you want a runtime sized bitset, check out boost::dynamic_bitset.
  • The sample is expected to work for files just by replacing istringstream by ifstream appropriately .

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.