C/C++编程:标准库bitset

刺骨的言语ヽ痛彻心扉 2022-05-19 10:44 422阅读 0赞

作用:提供了一种抽象方法来操作位的集合

若在编译时 bitset 的大小未知,则可使用 std::vector 或 boost::dynamic_bitset

构造函数

  1. #include <bitset>
  2. #include <string>
  3. #include <iostream>
  4. #include <climits>
  5. int main() {
  6. // 空构造函数
  7. std::bitset<8> b1; // [0,0,0,0,0,0,0,0]
  8. // unsigned long long 构造函数
  9. std::bitset<8> b2(42); // [0,0,1,0,1,0,1,0]
  10. std::bitset<70> bl(ULLONG_MAX); // [0,0,0,0,0,0,1,1,1,...,1,1,1] in C++11
  11. std::bitset<8> bs(0xfff0); // [1,1,1,1,0,0,0,0]
  12. // string 构造函数: 用 std::basic_string str 中的字符构造 bitset 。能提供可选的起始位置 pos 和长度 n
  13. std::string bit_string = "110010";
  14. std::bitset<8> b3(bit_string); // [0,0,1,1,0,0,1,0]
  15. std::bitset<8> b4(bit_string, 2); // [0,0,0,0,0,0,1,0]
  16. std::bitset<8> b5(bit_string, 2, 3); // [0,0,0,0,0,0,0,1]
  17. // 使用自定义零/一数字的 string 构造函数
  18. std::string alpha_bit_string = "aBaaBBaB";
  19. std::bitset<8> b6(alpha_bit_string, 0, alpha_bit_string.size(),'a', 'B'); // [0,1,0,0,1,1,0,1]
  20. // 使用自定义数字的 char* 构造函数
  21. std::bitset<8> b7("XXXXYYYY", 8, 'X', 'Y'); // [0,0,0,0,1,1,1,1]
  22. std::cout << b1 << "\nb2:" << b2 << "\nbl:" << bl << "\nbs:" << bs << '\n'
  23. << "b3:"<< b3 << "\nb4:" << b4<< "\nb5:" << b5 << "\nb6:" << b6 << '\n';
  24. }

20210302211535192.png

operator[]

作用:访问位于位置 pos 的位

  1. // bitset::operator[]
  2. #include <iostream> // std::cout
  3. #include <bitset> // std::bitset
  4. int main ()
  5. {
  6. std::bitset<4> foo;
  7. foo[1]=1; // 0010
  8. foo[2]=foo[1]; // 0110
  9. std::cout << "foo: " << foo << '\n';
  10. return 0;
  11. }
  12. //Output:
  13. //foo: 0110

test

作用:

返回pos位置的元素是否被设置,或者是否为1。返回值为true,或false。

不同于 operator[] ,它进行边界检查,且若 pos 不对应 bitset 中的合法位置则抛出 std::out_of_range 。

  1. #include <iostream>
  2. #include <bitset>
  3. int main()
  4. {
  5. std::bitset<10> b1("1111010000");
  6. size_t idx = 0;
  7. while (idx < b1.size() && !b1.test(idx)) {
  8. ++idx;
  9. }
  10. if (idx < b1.size()) {
  11. std::cout << "first set bit at index " << idx << '\n';
  12. } else {
  13. std::cout << "no set bits\n";
  14. }
  15. }

20210302212309322.png

  1. // bitset::test
  2. #include <iostream> // std::cout
  3. #include <string> // std::string
  4. #include <cstddef> // std::size_t
  5. #include <bitset> // std::bitset
  6. int main ()
  7. {
  8. std::bitset<5> foo (std::string("01011"));
  9. std::cout << "foo contains:\n";
  10. std::cout << std::boolalpha;
  11. for (std::size_t i=0; i<foo.size(); ++i)
  12. std::cout << foo.test(i) << '\n';
  13. return 0;
  14. }
  15. //Output:
  16. //foo contains:
  17. //true
  18. //true
  19. //false
  20. //true
  21. //false

all, any, none

检查是否全部、任一或无位被设为 true 。

1) 检查是否全部位被设为 true 。

2) 检查是否任一位被设为 true 。

3) 检查是否无位被设为 true

  1. #include <iostream>
  2. #include <bitset>
  3. int main()
  4. {
  5. std::bitset<4> b1("0000");
  6. std::bitset<4> b2("0101");
  7. std::bitset<4> b3("1111");
  8. std::cout << "bitset\t" << "all\t" << "any\t" << "none\n";
  9. std::cout << b1 << '\t' << b1.all() << '\t' << b1.any() << '\t' << b1.none() << '\n';
  10. std::cout << b2 << '\t' << b2.all() << '\t' << b2.any() << '\t' << b2.none() << '\n';
  11. std::cout << b3 << '\t' << b3.all() << '\t' << b3.any() << '\t' << b3.none() << '\n';
  12. }

20210302212541783.png

count

统计bitset中被设置的bits的个数,也就是bitset中值为1的元素个数。

  1. // bitset::count
  2. #include <iostream> // std::cout
  3. #include <string> // std::string
  4. #include <bitset> // std::bitset
  5. int main ()
  6. {
  7. std::bitset<8> foo (std::string("10110011"));
  8. std::cout << foo << " has ";
  9. std::cout << foo.count() << " ones and ";
  10. std::cout << (foo.size()-foo.count()) << " zeros.\n";
  11. return 0;
  12. }
  13. //Output:
  14. //10110011 has 5 ones and 3 zeros.

size()

返回bitset中元素总个数。即通常意义上bitset的大小。示例代码如下:

  1. // bitset::size
  2. #include <iostream> // std::cout
  3. #include <bitset> // std::bitset
  4. int main ()
  5. {
  6. std::bitset<8> foo;
  7. std::bitset<4> bar;
  8. std::cout << "foo.size() is " << foo.size() << '\n';
  9. std::cout << "bar.size() is " << bar.size() << '\n';
  10. return 0;
  11. }
  12. //Output:
  13. //foo.size() is 8
  14. //bar.size() is 4

&=,|=,^=,~

进行二进制与、或、异或及非。

1) 设置位为 *thisother 的位的对应对上二进制与的结果。

2) 设置位为 *thisother 的位的对应对上二进制或的结果。

3) 设置位为 *thisother 的位的对应对上二进制异或的结果。

4) 返回翻转所有位的 *this 的临时副本(二进制非)。

注意 &= 、 |= 、 和 ^= 仅对拥有相同大小 N 的 bitset 定义。

  1. #include <iostream>
  2. #include <string>
  3. #include <bitset>
  4. int main()
  5. {
  6. std::bitset<16> dest;
  7. std::string pattern_str = "1001";
  8. std::bitset<16> pattern(pattern_str);
  9. for (size_t i = 0, ie = dest.size()/pattern_str.size(); i != ie; ++i) {
  10. dest <<= pattern_str.size();
  11. dest |= pattern;
  12. }
  13. std::cout << dest << '\n';
  14. }

20210302213542954.png

operator&,|,^

进行二个 bitset lhsrhs 间的二进制与、或及异或。

1) 返回含 lhsrhs 的位对应对上的二进制与结果的 bitset<N>

2) 返回含 lhsrhs 的位对应对上的二进制或结果的 bitset<N>

3) 返回含 lhsrhs 的位对应对上的二进制异或结果的 bitset<N>

  1. #include <bitset>
  2. #include <iostream>
  3. int main()
  4. {
  5. std::bitset<4> b1("0110");
  6. std::bitset<4> b2("0011");
  7. std::cout << "b1 & b2: " << (b1 & b2) << '\n';
  8. std::cout << "b1 | b2: " << (b1 | b2) << '\n';
  9. std::cout << "b1 ^ b2: " << (b1 ^ b2) << '\n';
  10. }

" class="reference-link">20210302220142228.png

<<,<<=,>>,>>=

进行二进制左移和二进制右移。移入零。

  1. #include <iostream>
  2. #include <bitset>
  3. int main()
  4. {
  5. std::bitset<8> b("01110010");
  6. std::cout << "initial value: " << b << '\n';
  7. while (b.any()) {
  8. while (!b.test(0)) {
  9. b >>= 1;
  10. }
  11. std::cout << b << '\n';
  12. b >>= 1;
  13. }
  14. }

20210302213951960.png

<<,>>

从字符流插入或释出 bitset

  1. #include <bitset>
  2. #include <iostream>
  3. #include <sstream>
  4. int main()
  5. {
  6. std::string bit_string = "001101";
  7. std::istringstream bit_stream(bit_string);
  8. std::bitset<3> b1;
  9. bit_stream >> b1; // 读取 "001" ,流仍保有 "101"
  10. std::cout << b1 << '\n';
  11. std::bitset<8> b2;
  12. bit_stream >> b2; // 读取 "101" ,产出 8 位集为 "00000101"
  13. std::cout << b2 << '\n';
  14. }
  15. //001
  16. //00000101

set

设定bitset中某一个元素或者所有元素为1.

  1. #include <iostream>
  2. #include <bitset>
  3. int main()
  4. {
  5. std::bitset<8> b;
  6. for (size_t i = 1; i < b.size(); i += 2) {
  7. b.set(i);
  8. }
  9. std::cout << b << '\n';
  10. }
  11. // 10101010

reset()

将bitset中某一个元素或者所有元素重置为0

  1. // bitset::reset
  2. #include <iostream> // std::cout
  3. #include <string> // std::string
  4. #include <bitset> // std::bitset
  5. int main ()
  6. {
  7. std::bitset<4> foo (std::string("1011"));
  8. std::cout << foo.reset(1) << '\n'; // 1001
  9. std::cout << foo.reset() << '\n'; // 0000
  10. return 0;
  11. }
  12. //Output:
  13. //1001
  14. //0000

flip()

反转一个bitset

  1. // bitset::flip
  2. #include <iostream> // std::cout
  3. #include <string> // std::string
  4. #include <bitset> // std::bitset
  5. int main ()
  6. {
  7. std::bitset<4> foo (std::string("0001"));
  8. std::cout << foo.flip(2) << '\n'; // 0101
  9. std::cout << foo.flip() << '\n'; // 1010
  10. return 0;
  11. }
  12. //Output:
  13. //0101
  14. //1010

to_string

转换 bitset 的内容为 string

  1. #include <iostream>
  2. #include <bitset>
  3. int main()
  4. {
  5. std::bitset<8> b(42);
  6. std::cout << b.to_string() << '\n'
  7. << b.to_string('*') << '\n'
  8. << b.to_string('O', 'X') << '\n';
  9. }

to_ulong、to_ullong

将bitset转换成一个unsigned_long类型的数

  1. // bitset::to_ulong
  2. #include <iostream> // std::cout
  3. #include <bitset> // std::bitset
  4. int main ()
  5. {
  6. std::bitset<4> foo; // foo: 0000
  7. foo.set(); // foo: 1111
  8. std::cout << foo << " as an integer is: " << foo.to_ulong() << '\n';
  9. return 0;
  10. }
  11. //Output:
  12. //1111 as an integer is: 15
  13. #include <iostream>
  14. #include <bitset>
  15. #include <limits>
  16. int main()
  17. {
  18. std::bitset<std::numeric_limits<unsigned long long>::digits> b(
  19. 0x123456789abcdef0LL
  20. );
  21. std::cout << b << " " << std::hex << b.to_ullong() << '\n';
  22. b.flip();
  23. std::cout << b << " " << b.to_ullong() << '\n';
  24. }

20210302220021568.png

std::hash (std::bitset)

std::hash 对 std::bitset 的模板特化允许用户获得 std::bitset 类型的对象的哈希

  1. #include <iostream>
  2. #include <bitset>
  3. #include <functional>
  4. int main()
  5. {
  6. std::bitset<4> b1(1);
  7. std::bitset<4> b2(2);
  8. std::bitset<4> b3(b2);
  9. std::hash<std::bitset<4>> hash_fn;
  10. size_t h1 = hash_fn(b1);
  11. size_t h2 = hash_fn(b2);
  12. size_t h3 = hash_fn(b3);
  13. std::cout << h1 << '\n';
  14. std::cout << h2 << '\n';
  15. std::cout << h3 << '\n';
  16. }

20210302220429620.png

发表评论

表情:
评论列表 (有 0 条评论,422人围观)

还没有评论,来说两句吧...

相关阅读

    相关 bitset

    C++语言的一个类库,用来方便地管理一系列的bit位而不用程序员自己来写代码。 bitset除了可以访问指定下标的bit位以外,还可以把它们作为一个整数来进行某些统计。

    相关 标准非STL容器 : bitset

    1. 概念 什么是“标准非STL容器”?标准非STL容器是指“可以认为它们是容器,但是他们并不满足STL容器的所有要求”。前文提到的容器适配器stack、queue及pri

    相关 C++标准标准模板

      C++强大的功能来源于其丰富的类库及库函数资源。C++标准库的内容总共在50个标准头文件中定义。在C++开发中,要尽可能地利用标准库完成。这样做的直接好处包括:(1)成本: