0

我有一个由 1 和 0 组成的字符串,我用足够的 0 填充以使其长度完全可被 8 整除。我的目标是将此字符串转换为多个字节并以这样的方式对其进行排序,即我读取的第一个字符是最不重要的位,然后下一个是下一个最不重要的位,依此类推,直到我读取了 8 位,将其保存为一个字节,然后继续读取字符串,将下一位保存为第二个字节的最不重要的位。

例如,字符串“0101101101010010”的长度为 16,因此它将被转换为两个字节。第一个字节应该是“11011010”,第二个字节应该是“01001010”。

我不确定如何执行此操作,因为它不像反转字符串那么简单(我需要维护这些字节的顺序)。

任何帮助表示赞赏,谢谢!

4

3 回答 3

3

您可以通过字符串向后迭代,但像您建议的那样反转它可能更容易。从那里,您可以一次只构建一个字节。嵌套的 for 循环会很好地工作:

unsigned char bytes[8]; // Make sure this is zeroed
for (int i=0, j=0; i<str.length(); j++) {
  for (int k=0; k<8; k++, i++) {
    bytes[j] >>= 1;
    if (str[i] == '1') bytes[j] |= 0x80;
  }
}

i是当前字符串索引,j是当前字节数组索引,并k计算我们在当前字节中设置了多少位。如果当前字符为 1,则设置该位,否则不设置。重要的是字节数组是无符号的,因为我们使用的是右移。

于 2013-07-28T22:33:14.310 回答
0

您可以使用string::size / 8.

然后,这只是反转子字符串的问题。你可以这样做:

for(int i=0; i<number_of_bytes; i++)
{
  std::string temp_substr = original.substr(i*8,8);
  std::reversed = string(temp_substr.rbegin(),temp_substr.rend()) // using reverse iterators

  //now you can save that "byte" represented in the "reversed" string, for example using memcpy
}
于 2013-07-28T22:35:59.340 回答
0

取决于您是将其公开为通用函数还是将其封装在一个类中,以确保您应用了所有正确的约束,例如所有字符都是 0 或 1。

#include <cstdint>
#include <string>
#include <algorithm>
#include <iostream>

static const size_t BitsPerByte = 8;

// Suitable for a member function where you know all the constraints are met.
uint64_t crudeBinaryDecode(const std::string& src)
{
    uint64_t value = 0;
    const size_t numBits = src.size();
    for (size_t bitNo = 0; bitNo < numBits; ++bitNo)
        value |= uint64_t(src[bitNo] - '0') << bitNo;
    return value;
}

uint64_t clearerBinaryDecode(const std::string& src)
{
    static const size_t BitsPerByte = 8;
    if ((src.size() & (BitsPerByte - 1)) != 0)
        throw std::invalid_argument("binary value must be padded to a byte size");
    uint64_t value = 0;
    const size_t numBits = std::min(src.size(), sizeof(value) * BitsPerByte);
    for (size_t bitNo = 0; bitNo < numBits; ++bitNo) {
        uint64_t bitValue = (src[bitNo] == '0') ? 0ULL : 1ULL;
        value |= bitValue << bitNo;
    }
    return value;
}

int main()
{
    std::string dead("1011" "0101" "0111" "1011");
    std::string beef("1111" "0111" "0111" "1101");
    std::string bse ("1111" "0111" "0111" "1101" "1011" "0101" "0111" "1011" "1111" "0111" "0111" "1101" "1011" "0111" "0111" "1111");

    std::cout << std::hex;

    std::cout << "'dead' is: " << crudeBinaryDecode(dead) << std::endl;
    std::cout << "'beef' is: " << clearerBinaryDecode(beef) << std::endl;

    std::cout << "'bse'  is: " << crudeBinaryDecode(bse) << std::endl;

    return 0;
}
于 2013-07-28T23:05:12.990 回答