当前位置: 首页 > news >正文

C++语法中bitset位图介绍及模拟实现

一、位图的引入

先来看下边一道面试题:

给40亿个不重复的无符号整数,没排过序。给一个无符号整数,如何快速判断一个数是否在这40亿个数中。

经过我们之前的学习,我们可能会有以下的思路:

  • 对这些数进行排序,再通过二分算法,查找这个数是否存在

  • 插入到unordered_set中,使用find函数查找是否存在

上述方法看起来还不错,二分查找算法时间复杂度为logN,而插入到unordered_set中时间复杂度为O(N),而查找时时间复杂度为O(1),但是都有一个问题就是要将空间不足,40亿个无符号整形,需要160亿字节的空间,大概就是16GB的空间,一般计算机的内促都是4G或者8G,所以空间不足,此时就有了位图的方法来解决:

数据是否在给定的整形数据中,结果是在或者不在,刚好是两种状态,那么可以使用一个二进制比特位来代表数据是否存在的信息,如果二进制比特位为1,代表存在,为0代表不存在。比如:

对于上图来说,有一个整形数组,我们可以使用直接定址法对数组的数据进行映射,但是与之前不同的是,此时只是使用一个比特位来代表一个整形数据,当这个数存在时,比特位置1,不存在时,比特位置0,此时就可以大大节省空间资源,无符号整数只有2的32次方个,所以最多开2的32次方个空间,一个空间为一个比特,所以最终只需要512MB的空间。但是我们不能按照位来空间,最少必须一个字节,所以我们就每次开一个字节的空间,也就是8个比特位,将8位当做一个整体来处理,对要保存的数据除8就是第几个字节,对保存的数据模8就是在这个字节中的第几个位置。

二、位图的概念

所谓位图,就是用每一位来存放某种状态,适用于海量数据,数据无重复的场景。通常是用来判断某个数据存不存在的。

那么位图还有哪些应用呢?

  • 快速查找某个数据是否在一个集合中

  • 排序 + 去重

  • 求两个集合的交集、并集等

  • 操作系统中磁盘块标记

位图模拟实现

一、构造函数

由于不能按位开空间,所以我们选择每次开一个字节的空间,由于有范围最大为N,一位关联一个数据,所以需要开N/8个字节的空间,但是有时可能不能整除,所以要开N/8+1个字节的空间。所以

直接在构造函数中开好空间:

bitset(){_bits.resize(N / 8 + 1,0);}

二、set,reset,test函数

set函数的作用是对位图中的某一位进行填充

i就表示是第几个字节,而j表示该位在该字节中的第几位,所以对1进行左移j位后与该字节按位或,按位或的作用时不论该位为0还是为1,都将该位变为1。

void set(size_t x){int i = x / 8;int j = x % 8;_bits[i] |= (1 << j);}

reset的作用是将某一位清空

同样的将要清空的那一位置为0,进行按位与,不论原本该位是0还是1,都将该位置0

void reset(size_t x){int i = x / 8;int j = x % 8;_bits[i] &= ~(1 << j);}

test的作用是检测位图中某一位是否存在

bool test(size_t x){int i = x / 8;int j = x % 8;return _bits[i] & (1 << j);}

三、代码测试

void test_bit_set1(){bitset<100> bs1;bs1.set(8);bs1.set(9);bs1.set(20);cout << bs1.test(8) << endl;cout << bs1.test(9) << endl;cout << bs1.test(20) << endl;bs1.reset(8);bs1.reset(9);bs1.reset(20);cout << bs1.test(8) << endl;cout << bs1.test(9) << endl;cout << bs1.test(20) << endl;}

四、完整代码

namespace tmt
{template<size_t N>class bitset{public:bitset(){_bits.resize(N / 8 + 1,0);}void set(size_t x){int i = x / 8;int j = x % 8;_bits[i] |= (1 << j);}void reset(size_t x){int i = x / 8;int j = x % 8;_bits[i] &= ~(1 << j);}bool test(size_t x){int i = x / 8;int j = x % 8;return _bits[i] & (1 << j);}private:vector<char> _bits;};void test_bit_set1(){bitset<100> bs1;bs1.set(8);bs1.set(9);bs1.set(20);cout << bs1.test(8) << endl;cout << bs1.test(9) << endl;cout << bs1.test(20) << endl;bs1.reset(8);bs1.reset(9);bs1.reset(20);cout << bs1.test(8) << endl;cout << bs1.test(9) << endl;cout << bs1.test(20) << endl;}

相关文章:

C++语法中bitset位图介绍及模拟实现

一、位图的引入 先来看下边一道面试题&#xff1a; 给40亿个不重复的无符号整数&#xff0c;没排过序。给一个无符号整数&#xff0c;如何快速判断一个数是否在这40亿个数中。 经过我们之前的学习&#xff0c;我们可能会有以下的思路&#xff1a; 对这些数进行排序&#xff…...

Debezium系列之:深入理解消息过滤,实现过滤数据库删除事件,只采集数据库新增和更新事件

Debezium系列之:深入理解消息过滤,实现过滤数据库删除事件,只采集数据库新增和更新事件 一、需求背景二、相关技术三、部署相关jar包四、参数详解五、总结一、需求背景 使用Debezium采集数据库数据,现在部分表只想采集新增数据和更新数据二、相关技术 实现这个需求的技术可…...

Substack 如何在去中心化内容创作领域掀起波澜

面对数字内容广告化的困境&#xff0c;Substack回归做内容的初心&#xff0c;通过产品和平台双轮驱动&#xff0c;重塑一个去中心化的多元文化内容聚集地&#xff0c;实现了增长突破。其核心策略在于先使用简洁的创作工具赋能内容生产&#xff0c;进而通过平台的互动机制促进用…...

【MFC】07.MFC六大机制:消息映射-笔记

本专栏上两篇文章分别介绍了【MFC】05.MFC第一大机制&#xff1a;程序启动机制和【MFC】06.MFC第二大机制&#xff1a;窗口创建机制&#xff0c;这篇文章来为大家介绍MFC的第三大机制&#xff1a;消息映射 typfd要实现消息映射&#xff0c;必须满足的三个条件&#xff1a; 类必…...

python操作数据库

python操作数据库 首先安装数据插件 pip install pymysqlfrom pymysql import Connection # 引入数据库第三方包# 创建链接 conn Connection(host"localhost", # 主机名ipport3306,user"root",# 用户名password"123456" # 密码 )print(con…...

【C语言】小游戏-三字棋

大家好&#xff0c;我是深鱼~ 目录 一、游戏介绍 二、文件分装 三、代码实现步骤 1.制作简易游戏菜单 2.初始化棋盘 3.打印棋盘 4.玩家下棋 5.电脑随机下棋 6.判断输赢 7.判断棋盘是否满了 四、完整代码 game.h(相关函数的声明&#xff0c;整个代码要引用的头文件以及宏…...

多线程与并发编程面试题总结

多线程与并发编程 多线程 线程和进程的区别&#xff1f; 从操作系统层面上来讲&#xff1a;进程(process)在计算机里有单独的地址空间&#xff0c;而线程只有单独的堆栈和局部内存空间&#xff0c;线程之间是共享地址空间的&#xff0c;正是由于这个特性&#xff0c;对于同…...

在多页面应用和单页面应用中(例如vue)怎么提高seo搜索引擎优化

那么 我们要先知道 搜索引擎是怎么工作的&#xff1f; 搜索引擎是通过一系列步骤来工作的&#xff0c;以下是其基本原理&#xff1a; 1、网络爬虫&#xff1a;搜索引擎使用网络爬虫&#xff08;也称为蜘蛛、机器人&#xff09;来从互联网上抓取网页。网络爬虫按照预定义的规则…...

Dubbo 2.7.0 CompletableFuture 异步

了解Java中Future演进历史的同学应该知道&#xff0c;Dubbo 2.6.x及之前版本中使用的Future是在java 5中引入的&#xff0c;所以存在以上一些功能设计上的问题&#xff0c;而在java 8中引入的CompletableFuture进一步丰富了Future接口&#xff0c;很好的解决了这些问题。 Dubb…...

pytest-xdist分布式测试原理浅析

目录 pytest-xdist执行流程&#xff1a; pytest-xdist 模块结构&#xff1a; pytest-xdist分布式测试原理&#xff1a; pytest-xdist源码浅读&#xff1a; pytest-xdist执行流程&#xff1a; 解析命令行参数&#xff1a;pytest-xdist 会解析命令行参数&#xff0c;获取用户…...

研发工程师玩转Kubernetes——PVC通过storageClassName进行延迟绑定

不同的PV可以使用相同的StorageClass&#xff0c;它们是一对多的关系。 PV可以设置节点亲和性。比如下图&#xff0c;local-storage-class-waitforfirstconsumer-pv-ubuntuc只能在节点ubuntuc上&#xff1b;local-storage-class-waitforfirstconsumer-pv-ubuntud只能在节点ubu…...

6.利用matlab完成 符号矩阵的秩和 符号方阵的逆矩阵和行列式 (matlab程序)

1.简述 利用M文件建立矩阵 对于比较大且比较复杂的矩阵&#xff0c;可以为它专门建立一个M文件。下面通过一个简单例子来说明如何利用M文件创建矩阵。 例2-2 利用M文件建立MYMAT矩阵。(1) 启动有关编辑程序或MATLAB文本编辑器&#xff0c;并输入待建矩阵&#xff1a;(2) 把…...

python获取类名__qualname__,解决django接口ObjectDoesNotExist异常寻找model的问题

在django项目中&#xff0c;经常使用类似Model.objects.get(id1)的方法取对象&#xff0c;默认抛出的异常是ObjectDoesNotExist类型&#xff0c;通过try catch可以把异常捕获&#xff0c;获取的异常是Model.DoesNotExist类型&#xff0c; 要获知其类名&#xff0c;可以使用__na…...

电流的测量(分流电流表)

在当今的大多数仪器应用中&#xff0c;可以使用两种常见的电流测量方法&#xff1a;分流电流表方法和反馈电流表方法。分流电流表方法通常与通用数字万用表 (DMM)一起使用&#xff0c;用于测量分流电阻器上的电压测量值。该电压测量结果与已知的电阻值相结合&#xff0c;得出电…...

Leetcode每日一题:23. 合并 K 个升序链表(2023.8.12 C++)

目录 23. 合并 K 个升序链表 题目描述&#xff1a; 实现代码与解析&#xff1a; 优先级队列&#xff1a; 原理思路&#xff1a; 23. 合并 K 个升序链表 题目描述&#xff1a; 给你一个链表数组&#xff0c;每个链表都已经按升序排列。 请你将所有链表合并到一个升序链表…...

越南的区块链和NFT市场调研

越南的区块链和NFT市场调研 基本介绍 https://zh.wikipedia.org/wiki/%E8%B6%8A%E5%8D%97 语言文字&#xff1a; 越南语&#xff0c; 文字以国语字&#xff08;越南罗马字&#xff09;为主&#xff0c;汉喃文&#xff08;汉字&#xff09; 货币&#xff1a;越南盾 人口(2022…...

MySQL常用语句

当涉及到与关系型数据库进行交互时&#xff0c;以下是一些常用的 SQL 语句&#xff0c;可以帮助你进行数据查询、插入、更新和删除等操作&#xff1a; 查询数据&#xff1a; 查询所有数据&#xff1a;SELECT * FROM table_name; 查询特定列数据&#xff1a;SELECT column1, col…...

Mongodb:业务应用(1)

环境搭建参考&#xff1a;mongodb&#xff1a;环境搭建_Success___的博客-CSDN博客 需求&#xff1a; 在文章搜索服务中实现保存搜索记录到mongdb 并在搜索时查询出mongdb保存的数据 1、安装mongodb依赖 <dependency><groupId>org.springframework.data</groupI…...

【vue】vue中按钮权限控制:

文章目录 一、获取权限码二、三种按钮级别的权限控制方式【1】函数方式【2】组件方式【3】指令方式 一、获取权限码 要做权限控制&#xff0c;肯定需要一个code&#xff0c;无论是权限码还是角色码都可以&#xff0c;一般后端会一次性返回&#xff0c;然后全局存储起来就可以了…...

【博客695】k8s subPathExpr作用

k8s subPathExpr作用 场景&#xff1a; 对于一个deployment或者job拉起的服务&#xff0c;所有pod都是一样的配置&#xff0c;如果都挂载了宿主机的同一个目录&#xff0c;那么就会互相干扰&#xff0c;我们希望挂载相同目录&#xff0c;且在这个目录下&#xff0c;每个pod建立…...

xrdp终极指南:免费实现Windows到Linux的完美远程桌面连接

xrdp终极指南&#xff1a;免费实现Windows到Linux的完美远程桌面连接 【免费下载链接】xrdp xrdp: an open source RDP server 项目地址: https://gitcode.com/gh_mirrors/xrd/xrdp 想要从Windows电脑无缝访问Linux桌面环境吗&#xff1f;xrdp作为一款开源免费的RDP服务…...

从特征提取到微调:为什么你的BERT在MELD情感分类上效果差?我来帮你诊断

从特征提取到微调&#xff1a;为什么你的BERT在MELD情感分类上效果差&#xff1f;我来帮你诊断 当你第一次尝试用BERT处理MELD情感分类任务时&#xff0c;是否遇到过这样的困惑&#xff1a;明明使用了强大的预训练模型&#xff0c;F1分数却比论文报告的低了10%甚至更多&#xf…...

Ariadne测试策略:如何编写高质量的GraphQL API测试用例

Ariadne测试策略&#xff1a;如何编写高质量的GraphQL API测试用例 【免费下载链接】ariadne Python library for implementing GraphQL servers using schema-first approach. 项目地址: https://gitcode.com/gh_mirrors/ar/ariadne Ariadne是一个基于Python的GraphQL服…...

保姆级教程:在RV1126上搞定TP2855双摄驱动配置(从DTS到V4L2全流程)

RV1126双摄驱动实战&#xff1a;TP2855从硬件连接到V4L2调试全解析 当你在RV1126开发板上接入TP2855双摄像头模组时&#xff0c;是否遇到过图像采集不稳定、数据流中断或者驱动加载失败的问题&#xff1f;作为嵌入式Linux开发者&#xff0c;摄像头驱动配置往往是项目中最棘手的…...

C# 14原生AOT编译Dify客户端全链路优化(成本控制黄金公式首次公开)

第一章&#xff1a;C# 14原生AOT编译Dify客户端全链路优化概览C# 14 引入的原生 AOT&#xff08;Ahead-of-Time&#xff09;编译能力&#xff0c;为构建高性能、低延迟、零运行时依赖的 Dify 客户端提供了全新路径。与传统 JIT 编译相比&#xff0c;AOT 可将 C# 代码直接编译为…...

告别费马小定理!用线性递推法在C++里高效搞定逆元(附完整代码)

告别费马小定理&#xff01;用线性递推法在C里高效搞定逆元&#xff08;附完整代码&#xff09; 在算法竞赛和高性能计算领域&#xff0c;模运算中的逆元计算一直是困扰开发者的痛点。无论是计算组合数还是解决数论问题&#xff0c;传统方法往往面临效率瓶颈。想象一下&#xf…...

XueQiuSuperSpider实战:游资追踪与龙虎榜数据分析完整方案

XueQiuSuperSpider实战&#xff1a;游资追踪与龙虎榜数据分析完整方案 【免费下载链接】XueQiuSuperSpider 雪球股票信息超级爬虫 项目地址: https://gitcode.com/gh_mirrors/xu/XueQiuSuperSpider XueQiuSuperSpider是一款功能强大的雪球股票信息超级爬虫&#xff0c;专…...

HiveWE:重新定义魔兽争霸III地图编辑器的技术革命

HiveWE&#xff1a;重新定义魔兽争霸III地图编辑器的技术革命 【免费下载链接】HiveWE A Warcraft III world editor. 项目地址: https://gitcode.com/gh_mirrors/hi/HiveWE 在魔兽争霸III地图开发领域&#xff0c;传统编辑器面临着加载缓慢、操作卡顿和界面复杂的三大技…...

LxgwNeoXiHei特殊符号支持:易经、麻将、象棋符号全解析

LxgwNeoXiHei特殊符号支持&#xff1a;易经、麻将、象棋符号全解析 【免费下载链接】LxgwNeoXiHei A Chinese sans-serif font derived from IPAex Gothic. 一款衍生于「IPAexゴシック」的中文黑体字型。 项目地址: https://gitcode.com/gh_mirrors/lx/LxgwNeoXiHei Lxg…...

我用codex( GPT-5.4) 写代码一个多月后,突然开始害怕自己的项目了

我用 GPT-5.4 写代码一个多月后&#xff0c;突然开始害怕自己的项目了最近半年&#xff0c;我开发项目几乎 完全依赖 GPT-5.4。 写接口、写业务逻辑、写 SQL、写脚本、写测试代码&#xff0c; 甚至连 Jenkins Pipeline、Dockerfile、部署脚本都直接让 AI 生成。 效率确实很夸张…...