[C.C++] C++——bitset

27 0
Honkers 8 小时前 | 显示全部楼层 |阅读模式

顾名思义,bitset就是比特集合,用于位运算等操作。

固定长度,支持随机访问

同替他模板类一样,bitset的使用方法和其他模板类差别不大

bitset b        b有n位,被默认设置位0,n必须为常量表达式

bitset b(u)    b是unsigned long long 的低n位比特串拷贝,如果超出u的位数,剩余的被设置为0

有时候可能将字符串与比特串之间互相转换,可用到下面的构造函数

bitset b(s, pos, m, zero, one) 

b是string spos位开始m个字符的拷贝s只能包含zero/one, 否则会抛出一个invalid_arguement异常。字符在b中分别保存位zero one. pos默认值为0, m默认为std::string::npos,zero默认为'0', one 默认为'1'

bitset b(cp, pos, m, zero, one)

同上面的构造函数相同,但是从cp指向的字符数组中拷贝字符。如果没有提供m, 则cp必须指向一个C风格的字符串。如果提供了m,则从cp开始必须至少有m个zero/one字符

注意:上述两个构造函数,即接受string或者字符指针的构造函数是explicit的。在新标准中增加了为0和1指定其他字符的功能

演示

  1. #include <iostream>
  2. #include <bitset>
  3. #include <algorithm>
  4. using namespace std;
  5. int main()
  6. {
  7. const unsigned bit_num = 13;
  8. bitset<13> b1 (0xbeef);
  9. for(int i = bit_num -1;i>=0;--i)
  10. cout << b1[i];
  11. cout << endl;
  12. bitset<20> b2 (0xbeff);
  13. for(int i= 20-1;i>=0;--i)
  14. cout << b2[i];
  15. return 0;
  16. }
复制代码

运行结果

 演示

  1. #include <iostream>
  2. #include <bitset>
  3. using namespace std;
  4. int main()
  5. {
  6. string bit_string = "1001001100";
  7. //const unsigned bit_length = bit_string.length(); //error bit_length不能够编译时确定,所以他不是一个常量表达式
  8. bitset<10> b1 (bit_string); // b1 is 1001001100
  9. bitset<4> b2(bit_string,5,4,'0','1');
  10. for(int i = 4-1;i>=0;--i)
  11. {
  12. cout << b2[i];
  13. }
  14. cout << endl;
  15. bitset<4> b3(bit_string,bit_string.length()-4);
  16. for(int i=4-1;i>=0;--i)
  17. {
  18. cout << b3[i];
  19. }
  20. return 0;
  21. }
复制代码

 运行结果

可以看出,类似头迭代器和超尾迭代器的规则在bitset的构造时候依然适用 

先介绍一些概念

置位:将某一位设置为1

复位:将某一位设置为0

bitset方法

关于bitset的状态

.any()         是存在置位的二进制返回true

.none()        不存在置位的二进制返回true

.all()           所有位都置位返回true

.count()       返回置位的位数

.size()        一个constexpr函数,返回位数

.test(pos)   pos位为真返回true

关于设置bitset状态的函数

.set(pos,v)        设置pos位为v,v默认值为真值

.set()                无实参的情况下将所有位置位

.reset(pos)        复位pos位

.reset()                无实参的情况下复位所有位

.flip(pos)            切换pos位    

.filp()                   无实参的情况下切换所有位

b[pos]                下标访问

其它功能

返回一个unsigned long / unsigned long long值,如果b中位模式不能放入指定的结果类型,抛出一个overflow_error异常

.to_ulong()        

.to_ullong()

返回一个true为one flase为zero的字符串默认为'1', '0'

.to_string(zero, one)

os << b        将b中的二进制位打印到流os

is >> b         从is流中输入二进制位

演示

用一个bitset来存放10人的成绩及格状况

  1. #include <iostream>
  2. #include <bitset>
  3. #include <algorithm>
  4. #define grade_table GT
  5. using namespace std;
  6. int main()
  7. {
  8. const unsigned stu_num = 10;
  9. bitset<stu_num> grade_table;
  10. cin >> grade_table;
  11. if(GT.none()) //or !GT.any()
  12. cout << "没有人及格" << endl;
  13. else
  14. cout << "一共有" << GT.count() << "人及格" << endl;
  15. string bit_string = GT.to_string();
  16. cout << ".to_string()返回了一个比特字符串: " << bit_string << endl;
  17. cout << "老师大发慈悲,所有人都过了,好耶!" << endl;
  18. GT.set();
  19. cout << GT.to_string() << endl;
  20. GT.reset(1);
  21. cout << "但是一号小伙得罪了老师,老师没有给他过: " << GT.to_string() << endl;
  22. cout << "不知道将这个比特串转换为无符号整形有什么意义的操作" << GT.to_ulong();
  23. return 0;
  24. }
复制代码

运行结果

可以看见,适用bitset比适用传统的位运算要方便许多,不用我们自己设计mask,不用进行令人头疼的位移操作,甚至输入输出比特串也经为我们定义好了。

一些其他的东西

上面可以看出bitset为了泛型的功能,有着zero和one这两个东西,提供让用户自定义的功能

一些有趣的东西

  1. #include <iostream>
  2. #include <bitset>
  3. #include <algorithm>
  4. using namespace std;
  5. int main() {
  6. const string str = "ynynyynnyn";
  7. bitset<10> b(str, 0, string::npos, 'n', 'y');
  8. cout << b << endl;
  9. cout << b.to_string('n','y');
  10. return 0;
  11. }
复制代码

 可以猜猜运行的结果时什么

 相关链接

bitset - C++ Reference (cplusplus.com)

http://www.cplusplus.com/reference/bitset/bitset/?kw=bitset

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?立即注册

×
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

Honkers

特级红客

关注
  • 3237
    主题
  • 36
    粉丝
  • 0
    关注
这家伙很懒,什么都没留下!

中国红客联盟公众号

联系站长QQ:5520533

admin@chnhonker.com
Copyright © 2001-2025 Discuz Team. Powered by Discuz! X3.5 ( 粤ICP备13060014号 )|天天打卡 本站已运行