
C++
文章平均质量分 92
日常有关C++的学习记录
我太想进步了!!
所有默默扎根的日子,都是厚积薄发的过程
展开
-
C++ IO流
使用itoa函数进行转化。int a = 10;//将整型的a转化为十进制字符数字存储在字符串arr当中使用sprintf函数进行转化。int a = 10;//将整型的a转化为字符串格式存储在字符串arr当中虽然itoa函数和sprintf函数都能完成转化,但是在两个函数在转化时,都需要先给出保存结果的空间,而空间的大小是不太好界定的,除此之外,转化格式不匹配时,可能还会得到错误的结果甚至程序崩溃。在C++中,我们可以使用stringstream类对象来避开此问题。原创 2025-05-18 10:41:57 · 861 阅读 · 0 评论 -
unordered_map和unordered的介绍和使用
方式一: 指定key和value的类型构造一个空容器。//构造一个key为int类型,value为double类型的空容器方式二: 拷贝构造某同类型容器的复制品。//拷贝构造同类型容器um1的复制品方式三: 使用迭代器拷贝构造某一段内容。//使用迭代器区间构造方式一: 构造一个某类型的空容器。//构造int类型的空容器方式二: 拷贝构造某同类型容器的复制品。//拷贝构造同类型容器us1的复制品方式三: 使用迭代器拷贝构造某一段内容。//构造string对象某段区间的复制品。原创 2025-05-14 12:15:50 · 891 阅读 · 0 评论 -
哈希的应用 ——> 布隆过滤器
我们在使用新闻客户端看新闻时,它会给我们不停地推荐新的内容,它每次推荐时要去重,去掉 那些已经看过的内容。问题来了,新闻客户端推荐系统如何实现推送去重的?用服务器记录了用 户看过的所有历史记录,当推荐系统推荐新闻时会从每个用户的历史记录里进行筛选,过滤掉那 些已经存在的记录。如何快速查找呢?原创 2025-04-25 11:39:06 · 818 阅读 · 0 评论 -
【STL】bitset(位图) 的介绍,使用,模拟实现
给40亿个不重复的无符号整数,没排过序。给一个无符号整数,如何快速判断一个数是否在这40亿个数中?将这一堆数进行排序,然后通过二分查找的方法判断该数是否在这一堆数中。将这一堆数插入到unordered_set容器中,然后调用find函数判断该数是否在这一堆数中。单从方法上来看,这两种方法都是可以,而且效率也不错,第一种方法的时间复杂度是O (NlogN) ,第二种方法的时间复杂度是O(N)。但问题是这里有40亿个数,若是我们要将这些数全部加载到内存当中,那么将会占用16G的空间,空间消耗是很大的。原创 2025-04-24 23:21:36 · 669 阅读 · 0 评论 -
C++11 线程库
由于thread提供了移动赋值函数,因此当后续需要让该线程对象与线程函数关联时,可以以带参的方式创建一个匿名对象,然后调用移动赋值将该匿名对象关联线程的状态转移给该线程对象。线程函数的参数是以值拷贝的方式拷贝到线程栈空间中的,就算线程函数的参数为引用类型,在线程函数中修改后也不会影响到外部实参,因为其实际引用的是线程栈中的拷贝,而不是外部实参。当线程函数的参数类型为引用类型时,如果要想线程函数形参引用的是外部传入的实参,而不是线程栈空间中的拷贝,那么在传入实参时需要借助ref函数保持对实参的引用。原创 2025-04-23 21:45:53 · 963 阅读 · 0 评论 -
C++的类型转换
由于编译器认为const修饰的变量是不会被修改的,因此会将const修饰的变量存放到寄存器当中保存,当需要读取const变量是就会直接从寄存器中进行读取,而我们修改的实际上是内存中变量 a的值,因此打印出来的是修改之前变量a的值。上述代码中,如果传入fun函数的是子类对象的地址,那么在转换后pb1和pb2都会有对应的地址,但如果传入func函数的是父类对象的地址,那么pb1会有对应的地址,而pb2则会返回一个空指针。向上转换是语法天然支持的,不需要进行转换,而向下转换是语法不支持的,需要进行强制类型转换。原创 2025-03-02 22:53:13 · 992 阅读 · 0 评论 -
C++ —— 智能指针
内存泄漏指因为疏忽或错误造成程序未能释放已经不再使用的内存的情况。内 存泄漏并不是指内存在物理上的消失,而是应用程序分配某段内存后,因为设计错误,失去了对 该段内存的控制,因而造成了内存的浪费。内存泄漏的危害:长期运行的程序出现内存泄漏,影响很大,如操作系统、后台服务等等,出现 内存泄漏会导致响应越来越慢,最终卡死。原创 2025-01-03 16:53:19 · 1187 阅读 · 0 评论 -
C++异常处理
实际使用中很多公司都会自定义自己的异常体系进行规范的异常管理,因为一个项目中如果大家 随意抛异常,那么外层的调用者基本就没办法玩了,所以实际中都会定义一套继承的规范体系。这样大家抛出的都是继承的派生类对象,捕获一个基类就可以了最基础的异常类至少包含错误编号和错误描述两个成员变量,甚至还可以包含当前函数栈帧的调用链等信息。该异常类中一般都会提供两个成员函数,分别来获取错误编号和错误描述。public:, _id(id){}int GetErrid() const //获取错误id。原创 2024-12-27 22:15:44 · 1100 阅读 · 0 评论 -
【C++11】包装器
function包装器 也叫作适配器。C++中的function本质是一个类模板,也是一个包装器。Func();上面func可能是什么呢?那么func可能是函数名?函数指针?函数对象(仿函数对象)?也有可能 是lamber表达式对象?所以这些都是可调用的类型!如此丰富的类型,可能会导致模板的效率低下!为什么呢?我们继续往下看return x;return i;int main()//使用函数指针//使用仿函数//使用lambda表达式}, 30.0);return 0;原创 2024-12-26 09:49:08 · 1193 阅读 · 0 评论 -
【C++11】可变模板参数
template //Args全称:arguments返回类型 函数名(Args... args)//函数体下面就是一个基本可变参数的函数模板{}Args:是一个可变模板参数包args:是一个函数形参参数包模板参数Args前面有省略号,代表它是一个可变模板参数,我们将带省略号的参数称为“参数包”,这个参数包中可以包含0到任意个模板参数,args则是一个函数形参参数包。原创 2024-12-21 18:29:03 · 1440 阅读 · 39 评论 -
【C++11】lambda表达式
实际中我们使用[&]或[=]的方式捕获变量时,编译器也不一定会把父域中的所有变量捕获进来,编译器可能只会对lambda表达式中用到的变量进行捕获,它不会将用不到的变量捕获进来,主要看编译器的具体实现。就算加上mutable之后,x,y的const属性被取消了,但是使用传值的方式进行的捕获,是无法进行对两个局部变量进行值交换的。实际在底层,lambda表达式的处理方式和函数对象一样。其实可以看到在上面的代码中几个相同的lambda是相同的,类型也是不一样的,类型不一致也就是它们不能相互赋值的根本原因。原创 2024-12-15 16:30:35 · 812 阅读 · 14 评论 -
【C++11】类的新功能
C++11可以让我们更好的控制要使用的默认成员函数,假设在某些情况下我们需要使用某个默认成员函数,但是因为某些原因导致无法生成这个默认成员函数这时可以使用default关键字强制某个默认成员函数public:{}private:int main()Person p;return 0;实例化一个对象,没有给参数进行构造,编译器会报错,因为我们并没有在Person类中实现默认构造函数,并且我们实现了构造函数,编译器也不会自动生成默认构造函数。原创 2024-12-14 12:01:22 · 678 阅读 · 33 评论 -
【C++11】 右值引用和移动语义
左值是一个表示数据的表达式,如变量名或解引用的指针。原创 2024-12-10 23:22:32 · 6189 阅读 · 40 评论 -
【C++11】基础语法篇
这个容器没有提供很多的接口,它用于实现容器多参数类型的隐式转换。原创 2024-12-07 14:17:52 · 931 阅读 · 0 评论 -
【STL】用一张哈希表封装unordered_set和unordered_map
先创建一个哈希表,这里我们使用开散列实现哈希表,为了和库里的哈希表进行区分这里我将哈希表放入到了命名空间1.创建unordered_set和unordered_map,unordered_set和unordered_map分别是Key,Key模型和Key,Value模型,使用一张哈希表封装这两个的容器的话,我们需要同时兼容这两种模型。原创 2024-12-05 12:30:30 · 1576 阅读 · 0 评论 -
【STL】用一棵红黑树同时封装set和map
下面我们将对一颗kv模型的红黑树进行封装并且模拟实现出stl库当中的map和set以下是需要使用到的红黑树源代码:红黑树模板参数的控制我们知道set是一个k模型的容器,而map是一个kv模型的容器,那么我们如何使用一颗kv模型的黑红树来同时封装它们两个呢?我们需要控制我们传进红黑树中的模板参数,来进行对set和map的兼容为了和原红黑树的模板参数进行区分,这里我们将红黑树的第二个模板参数修改为TT可以是键值Key,也可以是键值对Key和Value,如果是set容器那么它传入底层红黑树的就是K原创 2024-11-28 19:37:48 · 791 阅读 · 0 评论 -
【STL】set,multiset,map,multimap的介绍以及使用
管方英文介绍:中文介绍:1. set是按照一定次序存储元素的容器,使用set的迭代器遍历set中的元素,可以得到有序序列2. 在set中,元素的value也标识它(value就是key,类型为T),并且每个value必须是唯一的。set中的元素不能在容器中修改(元素总是const),但是可以从容器中插入或删除它们。它的迭代器都是const_iterator3. 在内部,set中的元素总是按照其内部比较对象(类型比较)所指示的特定严格弱排序准则进行排序。原创 2024-11-14 12:46:31 · 1243 阅读 · 1 评论 -
【STL】priority_queue的使用和模拟实现
优先级队列(priority_queue)它也是一个容器适配器,默认使用的容器是vector,在往队列中放入数据时,它会将容器中放置的数据通过堆算法调整成 大堆/小堆,在使用时我们若不指定建堆方法,它默认会是排大堆(less)它的使用方法其实和stack,queue类似,只是priority_queue在插入元素的基础上进行了调整建堆3.不指定容器和底层使用的堆算法这时它的容器和堆算法默认使用的是vector和less成员函数功能push向队尾插入一个元素,并向上调整排序。原创 2024-11-10 10:45:35 · 467 阅读 · 0 评论 -
【STL】queue,stack的底层实现
在前面的介绍中我们已经知道了queue和stack是一个容器适配器,它并没有被划分到容器的行列,它只是对其他容器的再封装,在STL中queue和stack默认使用的容器是deque在数据结构的学习中,我们知道stack和queue可以使用顺序表和链表实现,若我们在这里定义一个vector让stack进行包装实现,实际上就是stack中的每个接口的实现都复用了vector的接口。原创 2024-11-09 11:39:17 · 610 阅读 · 0 评论 -
【C++】多态的语法与底层原理
多态是在不同继承关系的类对象,去调用同一函数,产生了不同的行为。1.必须通过基类的指针或者引用去调用虚函数2.被调用的函数必须是虚函数,且派生类必须对基类的虚函数进行重写被virtual修饰的成员函数称为:虚函数(只要成员函数才能变成虚函数)public:cout原创 2024-11-03 22:20:04 · 1054 阅读 · 0 评论 -
【C++】继承
继承(inheritance)机制是面向对象程序设计使代码可以复用的最重要的手段,它允许程序员在保持原有类特性的基础上进行扩展,增加功能,这样产生新的类,称派生类。继承呈现了面向对象程序设计的层次结构,体现了由简单到复杂的认知过程。以前我们接触的复用都是函数复用,继承是类设计层次的复用。teachert;s.Print();原创 2024-10-28 09:42:40 · 1293 阅读 · 0 评论 -
C++ —— 《模板进阶详解》,typename和class的用法,非类型模板参数,模板的特化,模板的分离编译
一个程序(项目)由若干个源文件共同实现,而每个源文件单独编译生成目标文件,最后将所有目标文件链接起来形成单一的可执行文件的过程称为分离编译模式。【优点】1. 模板复用了代码,节省资源,更快的迭代开发,C++的标准模板库(STL)因此而产生2. 增强了代码的灵活性【缺陷】1. 模板会导致代码膨胀问题,也会导致编译时间变长2. 出现模板编译错误时,错误信息非常凌乱,不易定位错误。原创 2024-10-22 22:02:36 · 1240 阅读 · 0 评论 -
【STL】Queue和stack的介绍及使用
queue的介绍队列作为容器适配器实现,容器适配器即将特定容器类封装作为其底层容器类,queue提供一组特定的 成员函数来访问其元素。元素从队尾入队列,从队头出队列。底层容器可以是标准容器类模板之一,也可以是其他专门设计的容器类。该底层容器应至少支持以下操 作:empty:检测队列是否为空size:返回队列中有效元素的个数front:返回队头元素的引用back:返回队尾元素的引用push_back:在队列尾部入队列pop_front:在队列头部出队列。原创 2024-10-19 09:57:37 · 371 阅读 · 0 评论 -
【STL】模拟实现list
因为迭代器·结点指针的行为不能满足迭代器定义,那么我们可以对这个结点指针进行封装,对结点指针的各种运算符进行重载,使得我们可以像使用string和vector当中的迭代器一样去使用list当中的迭代器。当我们使用解引用操作符时,是想得到该位置的数据内容,所以我们直接返回当前结点指针所指向的数据即可,但是这里需要解引用返回,得到数据之后,我们后面可能会对这个数据进行修改。对于后置--,我们需要记录结点指针当前的位置,让结点指针向指向前一个结点,然后返回自减前的结点指针即可。原创 2024-10-14 12:00:00 · 2632 阅读 · 0 评论 -
【STL】vector的模拟实现
reserve函数的实现思路也是很简单的,先判断所给n是否大于当前容器的最大容量(否则无需进行任何操作),操作时直接开辟一块可以容纳n个数据的空间,然后将原容器当中的有效数据拷贝到该空间,之后将原容器存储数据的空间释放,并将新开辟的空间交给该容器维护,最好更新容器当中各个成员变量的值即可。erase函数可以删除所给迭代器pos位置的数据,在删除数据前需要判断容器释放为空,若为空则需做断言处理,删除数据时直接将pos位置之后的数据统一向前挪动一位,将pos位置的数据覆盖即可。原创 2024-10-10 15:48:37 · 1236 阅读 · 0 评论 -
【STL】vector的介绍及使用
一、vector的介绍1. vector是表示可变大小数组的序列容器。2. 就像数组一样,vector也采用的连续存储空间来存储元素。也就是意味着可以采用下标对vector的元素 进行访问,和数组一样高效。但是又不像数组,它的大小是可以动态改变的,而且它的大小会被容器自 动处理。3. 本质讲,vector使用动态分配数组来存储它的元素。当新元素插入时候,这个数组需要被重新分配大小 为了增加存储空间。其做法是,分配一个新的数组,然后将全部元素移到这个数组。原创 2024-10-07 15:38:38 · 986 阅读 · 1 评论 -
经典OJ题——string(二) 反转字符串II,反转字符串中的单词III
给定一个字符串s和一个整数k,从字符串开头算起,每计数至2k个字符,就反转这2k字符中的前k个字符。k2kkk"bacdfeg""bacd"这题就是区间翻转,确定好范围,利用reverse函数来实现翻转区间字符串,注意:reverse是左闭右开,情况1:字符串总大小小于或等于k,我们就让前k个字符翻转情况2:如果剩余字符串的大小小于k,就翻转整个字符串。原创 2024-10-06 12:00:00 · 374 阅读 · 0 评论 -
【C++】认识匿名对象
在C++中,匿名对象是指在没有呗命名的情况下创建的临时对象。它们通常在单个语句中执行一系列操作或调用某个函数,并且不需要将结果存放进变量中。匿名对象的创建非常简单,在类名后加一对括号,匿名对象就诞生了一、对匿名对象的解读类名();//有名对象A(10);//匿名对象A b(10);//有名对象return 0;原创 2024-10-05 10:00:00 · 1382 阅读 · 0 评论 -
【STL】 string底层实现,了解接口如何工作
创建tmp对象,使用str的动态资源进行初始化,然后与_str进行交换,这样就全自动的进行了拷贝,这里需要注意的是必须让_str在初始化列表进行初始化,因为每个编译器在对象实例化的时候都可能会有自己的个性化处理(帮对象初始化),但是C++语法规定,构造函数不会去初始化自置类型,自定义会去调用它的构造函数,相信编译器很不靠谱,所以为了增强代码的可移植性最好的方法是我们手动进行初始化。若是找到了目标字符串,我们可以通过计算目标字符串的起始位置和对象C字符串的起始位置的差值,进而得到目标字符串起始位置的下标。原创 2024-10-04 18:52:34 · 681 阅读 · 0 评论 -
经典OJ解析—— string类 (一)仅仅反转字母,字符串中的第一个唯一字符,最后一个单词的长度,验证回文串,字符串相加
给你一个字符串s,由若干单词组成,单词前后用一些空格字符隔开。返回字符串中最后一个单词的长度。单词是指仅由字母组成、不包含任何空格字符的最大 子字符串。示例 2:4最后一个单词是“moon”,长度为 4。s仅有英文字母和空格' '组成s中至少存在一个单词字符串中至少有一个单词,我们需要先找到最后一个单词的最后一个字母,然后从后开始往前遍历字符串,直到遇到空格或到达字符串起始位置结束public:--index;原创 2024-10-02 16:26:09 · 1059 阅读 · 0 评论 -
【STL】string的介绍以及使用
是C++标准库的重要组成部分,不仅是一个可复用的组件库,而且是一个包罗数据结构与算法的软件框架。string();//构造一个空字符串//使用一个已经存在的对象拷贝构造给另一个对象//分割字符串//使用常量字符串实例化一个对象//从第一个元素开始取得向后的元素,限制个数//复制C字符,复制n个//实例化一个空字符对象//使用常字符串给对象初始化,对象实例化//用一个已经存在的对象给另外一个对象拷贝构造//分割字符串。原创 2024-09-24 23:28:15 · 1493 阅读 · 1 评论 -
C++--模板(template)详解—— 函数模板与类模板
class类模板名//类内成员定义类成员函数声明和定义分离class Datepublic:Date();int _month;int _day;//普通类:类名和类型一样//类模板:类名和类型不一样//类模板 类名:Date 类型:Date (类型是类名加):_year(1),_month(1),day(1)类模板中函数放在类外进行定义时,需要加模板参数列表。原创 2024-09-22 23:05:53 · 1193 阅读 · 0 评论 -
C\C++内存管理详解
(1)动态申请单个类的空间:使用malloc和freefree(p1);使用new和deletedelete p1;(2)动态申请多个内存空间使用malloc和freefree(p1);使用new和delete(3)动态申请多个内存空间并初始化方法一:使用匿名对象初始化如果只给了三给对象初始化的值,编译器不会帮你将最后一个初始化对于自定义类型来说,原创 2024-09-21 20:48:55 · 1199 阅读 · 0 评论 -
C++类与对象(三)
若类中。原创 2024-09-20 11:27:36 · 1075 阅读 · 0 评论 -
C++类与对象(二)超详细
class Date//声明友元函数,在类中哪定义都可以public:_day = day;int _month;int _day;return in;这条语句中的参数都不可以加constin是向对象d中写数据,d不能加const写数据的过程中会改变in中的一些状态值,in不能加const。原创 2024-09-15 11:43:42 · 1541 阅读 · 0 评论 -
C++类与对象(一)
class Date//声明友元函数,在类中哪定义都可以public:_day = day;int _month;int _day;return in;这条语句中的参数都不可以加constin是向对象d中写数据,d不能加const写数据的过程中会改变in中的一些状态值,in不能加const。原创 2024-09-12 15:52:54 · 925 阅读 · 0 评论 -
C++领进门(第三讲)
使用auto修饰的变量,是具有自动存储器的局部变量,但遗憾的 是一直没有人去使用它,大家可思考下为什么?auto不再是一个存储类型指示符,而是作为一 个新的类型指示符来指示编译器,auto声明的变量必须由编译器在编译时期推导而得,即:auto可以自动推导出右边表达式的类型int main()int a = 0;int b = a;auto c = a;// 根据右边的表达式自动推导c的类型// 根据右边的表达式自动推导d的类型return 0;原创 2024-08-29 16:58:37 · 1302 阅读 · 0 评论 -
C++领进门(第二讲)
引用不是新定义一个变量,而是给已存在变量取了一个别名,编译器不会为引用变量开辟内存空 间,它和它引用的变量共用同一块内存空间。如: 孙悟空也叫齐天大圣,引用(别名)的意思就是跟你起了一个外号如: int& b = a;这里b就是a的引用(别名)例:测试运行:由上图可知a和b确实是在一个内存空间注:引用类型必须和引用实体是同种类型的 1. 引用在定义时必须初始化测试运行: 2. 一个变量可以有多个引用 测试运行:值也是相同的这是对a进行多次引用,给d和c自加就等于a自加3. 引用一旦引用原创 2024-08-27 17:37:51 · 903 阅读 · 0 评论 -
C++领进门(第一讲)
定义命名空间,需要使用到namespace关键字,后面跟命名空间的名字,然后接一对{}即可,{} 中即为命名空间的成员。1. 正常的命名空间定义// 命名空间中可以定义变量/函数/类型// 变量//函数//结构体类型int val;nxbw是命名空间的名字,一般开发中是用项目名字做命名空间名。2. 命名空间可以嵌套int a;int b;int c = 3;int d;原创 2024-08-25 16:33:46 · 1249 阅读 · 0 评论