我正在尝试在二进制字符串中设置位。我最初有一个空字符串,需要在字符串中设置给定位(i)。
对于给定的示例,输出应为0x3001
as:
pos: 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
bit: 0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 1
^ ^
MSB LSB
其中,十六进制为3001
。
#include<iostream>
#include<string>
#include<sstream>
#include<iomanip>
using namespace std;
void generate_string(string& s,int i){
int sl = s.length();
int x = i/8;
std::stringstream m(s, ios_base::app);
if(sl<x){
for(int j = x-sl;j>=0;j--){
m<<'\x00';
}
}
s = m.str();
s[x] |= 1 << i%8;
}
int main(){
string s = "";
generate_string(s,15);
generate_string(s,2);
generate_string(s,3);
for(int i=0;i<s.length();i++)
cout<<hex<<(int)s[i];
return 0;
}
但是这个程序没有显示任何输出。
答案 0 :(得分:1)
它实际上比你想象的要简单得多。唯一复杂的部分是计算要在字节中设置的位数。
哦,为什么要使用字符串呢?为什么不是vector?
以下是我的解决方案,改为使用std::vector
:
void set_bit(std::vector<uint8_t>& bits, unsigned bit)
{
static unsigned const bit_count = 8; // Should really use std::numeric_limits<uint8_t>::digits
unsigned index = bit / bit_count;
while (index + 1 > bits.size())
bits.push_back(0);
// Since the bit-numbers are reversed from what's "common",
// we need a little more complex calculation here.
// bit % bit_count to get the "normal" bit number
// bit_count - bit % bit_count to reverse the bit numbering
// Then -1 to get a number between 0 and 7
bits[index] |= 1 << (bit_count - bit % bit_count - 1);
}
您可以使用std::string
使用类似的解决方案,但我不明白为什么。
答案 1 :(得分:1)
也许是这样的?
#include<iostream>
#include<string>
using namespace std;
void set_bit(string& s,int i){
auto bits = ((i + 7) / 8) * 8;
if (bits > s.length())
{
auto diff = bits - s.length();
s += std::string(diff, '0');
}
s[i] = '1';
}
int main(){
string s;
set_bit(s, 2);
set_bit(s, 3);
set_bit(s, 15);
cout << s << endl;
return 0;
}
预期产出:
0011000000000001
更新:尝试2: - )
#include<iostream>
#include<iomanip>
#include<string>
using namespace std;
void set_bit(string& s,int i){
auto bytes = (i + 7) / 8;
if (bytes > s.length())
{
auto diff = bytes - s.length();
s += std::string(diff, 0);
}
s[i / 8] |= char(1 << (7-(i%8)));
}
int main(){
string s;
set_bit(s, 2);
set_bit(s, 3);
set_bit(s, 15);
std::cout << "as hex: ";
for (auto c : s) {
cout << hex << setfill('0') << setw(2) << (int(c) & 0xff);
}
cout << endl;
std::cout << "as binary: ";
auto sep = "";
for (auto c : s) {
unsigned char bits = c;
for (unsigned char mask = 0x80 ; mask ; mask >>= 1)
{
cout << sep << ((bits & mask) ? '1' : '0');
sep = " ";
}
}
cout << endl;
return 0;
}
预期产出:
as hex: 3001
as binary: 0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 1
答案 2 :(得分:0)
我不太明白你的问题输出应该是什么,因为你在样本输入/输出中混合了大多数/最少有意义的位和半字节顺序,但是我想以十六进制的形式打印数字作为你可以这样做:
#include <iostream>
#include <string>
#include <sstream>
#include <algorithm>
void feed(std::string& s, int x){
unsigned int mask = 15;
int nibblesInWord = sizeof(void*)*16;
std::stringstream ss;
while(nibblesInWord--){
std::cout << int(x & mask) <<std::endl;
ss << int(x & mask);
x >>= 4;
}
s = ss.str();
std::reverse(s.begin(), s.end());
}
int main(){
std::string s;
feed(s, 99);
std::cout << s <<std::endl;
}