自定义博客皮肤VIP专享

*博客头图:

格式为PNG、JPG,宽度*高度大于1920*100像素,不超过2MB,主视觉建议放在右侧,请参照线上博客头图

请上传大于1920*100像素的图片!

博客底图:

图片格式为PNG、JPG,不超过1MB,可上下左右平铺至整个背景

栏目图:

图片格式为PNG、JPG,图片宽度*高度为300*38像素,不超过0.5MB

主标题颜色:

RGB颜色,例如:#AFAFAF

Hover:

RGB颜色,例如:#AFAFAF

副标题颜色:

RGB颜色,例如:#AFAFAF

自定义博客皮肤

-+
  • 博客(30)
  • 收藏
  • 关注

原创 O (1) 查找神技!哈希表核心玩法全解析,闭散列 + 开散列实战代码直接抄

本文介绍了哈希表的基本概念及实现方法。哈希表通过哈希函数建立元素与存储位置的映射关系,实现高效查找(O(1)时间复杂度)。主要内容包括:1)哈希冲突的概念及原因;2)常用哈希函数如直接定址法和除留余数法;3)两种解决冲突的方法 - 闭散列(线性探测)和开散列(链地址法),并给出具体实现代码。重点分析了扩容机制,当负载因子超过0.7时需要扩容重建哈希表。哈希表通过空间换时间的策略,大幅提升了查找效率。

2025-11-15 22:41:16 671 8

原创 踩爆 8 个坑后,我悟了!unordered_map 底层封装的正确姿势(代码可直接抄)

本文介绍了如何从基础的KV模型哈希表逐步改造为支持泛型T的哈希桶,最终封装成unordered_map和unordered_set。主要步骤包括:1) 将节点从pair<K,V>抽象为泛型T;2) 引入KeyOfT策略类从T中提取key;3) 实现通用哈希桶HashTable<K,T,KeyOfT,Hash>;4) 添加迭代器支持;5) 封装具体容器类。文章特别指出了实现过程中的常见错误,如节点类型使用不当等。通过这种分层设计,可以复用同一套哈希桶实现来支持不同的关联容器需求。

2025-11-15 22:40:41 1129 3

原创 不再死记!红黑树默认红色的原理 + LL/RR/LR/RL 全图解

红黑树是一种自平衡二叉搜索树,通过节点颜色(红/黑)和旋转操作维护平衡。本文介绍了红黑树的基本概念、性质(根黑、无连续红、路径同黑数),对比了AVL树与BST的差异,突出了红黑树在插入删除效率上的优势。详细解析了插入操作的实现逻辑:新节点默认红色,若父节点为红则需调整,分"叔叔红"(变色)和"叔叔黑"(旋转+变色)两种情况处理,并给出LL/RR/LR/RL四种旋转场景的图示与代码实现。文中附有节点定义示例和完整插入代码,强调红黑树通过适度放宽平衡条件换取更高操作效率的

2025-11-01 19:53:48 1820 23

原创 别再让搜索树变竹竿!AVL 旋转四连招详解!

摘要:AVL树是一种自平衡二叉搜索树,通过平衡因子(右子树高度-左子树高度)确保每个节点平衡因子的绝对值≤1。当插入或删除导致树失衡(平衡因子为±2)时,通过旋转操作(右旋、左旋等)恢复平衡。文章详细分析了AVL树的结构定义、插入逻辑以及旋转操作(以右旋为例),展示了如何通过调整子树高度保持高效操作性能,解决普通二叉搜索树退化为链表的问题,实现O(logn)的时间复杂度。

2025-10-30 20:00:53 929 49

原创 初学二叉搜索树踩坑多?C++ 从原理到代码,搞定增删查全流程

本文介绍了二叉搜索树的基本概念和操作实现。二叉搜索树满足左子树节点值小于根节点值,右子树节点值大于根节点值的特性。文章详细讲解了查找、插入和删除三种核心操作:查找采用二分思想,时间复杂度为O(logn);插入需找到合适位置并保持树结构;删除则根据节点子节点数量分为三种情况处理,重点阐释了删除有两个子节点时的替换策略。通过C++代码示例展示了二叉搜索树类的具体实现方法,包括节点结构定义和各类操作的算法流程。

2025-10-27 13:11:16 1584 52

原创 “码”上认亲!面向对象之多态:一脉相承的「同名不同用」

文章摘要:本文介绍了C++多态的概念及实现方式。通过虚函数机制,可以让不同类型的对象执行相同行为时产生不同结果。重点讲解了基类析构函数声明为虚函数的重要性,以避免内存泄漏问题。同时介绍了C++11引入的override和final关键字,用于确保正确重写虚函数或禁止重写。文章还分析了多态的实现条件,包括基类虚函数重写、基类指针或引用调用虚函数等关键点。

2025-10-23 16:01:19 723 15

原创 “码” 上认亲!面向对象之继承:解锁代码的 “家族传承” 密码

本文介绍了C++中继承的基础知识,主要包含以下内容: 继承的定义:继承是面向对象程序设计中实现代码复用的重要手段,允许在保持原有类特性的基础上进行扩展。 继承语法:通过示例展示了鱼类基类(Fish)和派生类(Carp、Tuna)的实现方式,解释了protected限定符的作用。 基类初始化:演示了如何使用派生类构造函数通过初始化列表向基类传递参数。 方法覆盖:说明如何在派生类中覆盖基类方法,并提供了畜牧业动物类的示例。 显式调用:介绍了如何在派生类中通过作用域限定符显式调用基类方法。 文章通过多个具体代码示

2025-10-20 17:23:06 890 51

原创 字符串相关OJ题解析(图文并茂+过程演示)

本文介绍了常见的字符串算法处理方法

2025-10-18 16:02:36 1056 50

原创 别再被模板折磨了:非类型参数 + 特化 + 分离编译一网打尽

本文介绍了C++模板中的非类型模板参数和模板特化两大特性。非类型模板参数允许将编译期确定的值作为模板参数,常用于静态数组大小配置,如std::array<T,N>的实现。模板特化则针对特定类型提供定制化实现,包括函数模板特化(需保持参数类型一致)和类模板特化(分全特化和偏特化)。全特化完全指定所有模板参数,偏特化可针对参数组合(如指针类型或固定部分参数)进行特化处理。通过特化能解决特殊类型场景下的问题,如指针比较的误判情况。文中通过日期类比较、类模板特化等示例代码,直观展示了这些特性的应用场景和

2025-10-14 12:46:35 972 20

原创 从底层到上层的“外挂”:deque、stack、queue、priority_queue 全面拆解

这篇文章主要介绍了C++中的容器适配器及其底层实现原理。主要内容包括: 容器适配器概念:通过封装现有容器,提供特定接口(如栈的LIFO、队列的FIFO特性),是一种设计模式。 三种标准适配器: stack:默认基于deque实现 queue:默认基于deque实现 priority_queue:默认基于vector实现(大根堆) deque详解: 分块存储+指针表的结构 优缺点分析:头尾操作高效但遍历性能较差 作为stack/queue默认容器的原因 stack模拟实现:展示如何基于现有容器封装适配器接口

2025-10-13 16:54:32 552 47

原创 万字长文带你从0到实战,全面吃透八大排序算法

从底层到实战,图文并茂详解八大排序算法

2025-10-10 19:02:45 758 28

原创 二叉树实战笔记:结构、遍历、接口与 OJ 实战

本文聚焦 “二叉树实战”,系统覆盖从基础到应用全流程。先铺垫树的基础概念(节点度、层次等)及特殊二叉树(满、完全二叉树)特性;再用 C++ 模板实现二叉树节点结构体与类,手搓1-2-3/4-5-6示例树,展示内存组织逻辑。核心解析遍历技术:前中后序递归遍历(根左右 / 左根右 / 左右根)的 “递 - 归” 思想,及层序遍历的队列应用;实战含 LeetCode 题解(单值、相同树、对称树、子树)与常用接口(最大深度、节点总数、k 层节点数、值查找)。

2025-10-05 21:01:27 1268 46

原创 从堆到TopK:一文吃透核心原理与实战应用

本文系统介绍了树和堆的数据结构及其核心原理。主要内容包括:1)树的基本概念与术语,如节点度、层次、深度等;2)二叉树的定义与特殊类型(满二叉树、完全二叉树);3)堆的本质是完全二叉树,分为大顶堆和小顶堆;4)堆的底层实现依赖动态数组和两个核心操作:向上调整(用于插入元素)和向下调整(用于删除堆顶),通过索引关系高效维护堆结构;5)介绍了两种建堆方法的时间复杂度差异。文章通过图示和代码示例详细说明了堆的调整过程,为理解优先队列等高级数据结构奠定了基础。

2025-10-04 20:03:43 1220 29

原创 从直线到环形:解锁栈、队列背后的空间与效率平衡术

本文介绍了两种经典数据结构——栈和队列的底层实现与特性。栈采用后进先出(LIFO)原则,可通过动态数组或链表实现,支持压栈、出栈等高效操作,常用于函数调用、撤销操作等场景。队列遵循先进先出(FIFO)原则,但数组实现会面临"假溢出"问题。为此,文中提出循环队列的解决方案,通过首尾相连提高空间利用率。文章通过C++代码展示了栈和队列的具体实现,并探讨了它们在实际应用中的价值,体现了数据结构从简单到优化的演进过程。

2025-10-02 18:28:58 929 28

原创 list 迭代器:C++ 容器封装的 “行为统一” 艺术

在C++标准库中,std::list是双向链表的容器,我们日常用就能方便地插入删除,但它的底层实现究竟是什么样的?尤其是迭代器(iterator),为什么it!=lst.end();++it)可以统一操作链表?今天,我基于一个精简版mini_list的实现,重点解析迭代器封装的底层思想,带大家从零实现并理解list容器。在mini_list中,通过实例化public:// 可写迭代器:ref=T&,ptr=T*// 只读迭代器:ref=const T&,ptr=const T*// ...

2025-09-25 11:50:26 2169 40

原创 深度剖析 vector 底层原理:从手写实现到核心技术点全解析

在C++标准模板库(STL)中,vector是最常用的容器之一,它以动态数组的形式存在,兼顾了数组的随机访问效率和动态扩容的灵活性。很多开发者日常使用vector时,往往只关注其表层接口,却对其底层实现原理一知半解。本文将通过手写一个简化版vectormy_vector),深入剖析vector的底层机制,重点讲解内存管理、深浅拷贝、迭代器失效、构造函数设计、交换机制等核心技术点,和大家交流我的一些理解。核心结构:以_start(内存起始)、_finish(元素末尾)、(容量末尾)三个指针为基础,

2025-09-21 14:43:29 1174 31

原创 揭秘整数内存密码:从原码到补码,读懂计算机 “数字语言”

在C/C++语言中,有很多种类型,而整型是用的最多的int num;// 声明一个整型变量// 声明并初始化一个变量// 先声明一个变量 再赋值int exm;// 声明一个变量,它的值是随机的exm = 10;// 给这个变量赋值上面这两行代码和的作用是一样的,但是赋值和初始化是两个不同的操作,赋值是给已经存在的变量进行操作,初始化是在变量定义时进行操作int x = -1;return 0;对于变量x = -1在内存中,-1当用%u。

2025-09-13 21:58:10 942 28

原创 进制间的转换

假如说一个十六进制数为0x3F,将其转换为十进制,此时的权重基础是16的几次方了。二进制有个缺点就是表示起来数据过于冗长,而十六进制就能缩短数据表示,更为简洁。不断除以16找到余数,直到除到0为止,从下到上是高位到低位的顺序。不断除以2找到余数,直到除到0为止,从下到上是高位到低位的顺序。八进制数在计算机科学中并不常用,转换方法同上,就不再赘述了。八进制数在计算机科学中并不常用,转换方法同上,就不再赘述了。这六个数,为了和其他进制区分,以0x开头,例如。组成,为了和其他进制区分,以。

2025-09-13 10:38:25 779 19

原创 从零实现一个简化版string 类 —— 深入理解std::string的底层设计

说明:本文聚焦 的实现细节与设计理由,代码使用一个教学用的 ,并配有完整实现与测试用例。不讲 API 用法,而是解释“为什么要这么实现”。在 C++ 开发中, 就像“空气”一样无处不在:拼接日志、处理配置、解析数据…… 我们随手就能写 、,却很少追问为什么这些操作有特定的性能特征。本文不讲“如何用 string”,而讲为什么要这样设计 string。我们用教学版 来逐步展示 的核心实现思想:内存布局、扩容策略、拷贝/移动语义、迭代器规则等。读完你应当能回答:为什么 在大多数情况下是 O(1)?为什么

2025-09-10 22:48:46 1167 22

原创 链表相关OJ题

思路:创建一个哨兵位指向head,创建一个cur临时指针,遍历链表,遇到等于val的节点跳过即可,最后返回即链表的头节点创建一个哨兵位就避免了讨论head是否为空。

2025-09-01 20:35:54 1233 19

原创 链表漫游指南:C++ 指针操作的艺术与实践

上一章的顺序表底层是数组,封装了增删查改的功能接口成为了顺序表。存储顺序表的空间是连续的,顺序表非常大时,内存可能无法提供这么大的连续空间,由此,链表就被创造了。在一个复杂的系统中,空闲的内存空间散落在内存各处,而链表通过指针很好的链接起了各个分散的内存空间。如图:内存空间分配并不连续,但是指针称为维系各个空间的桥梁。

2025-08-23 13:35:07 1426 21

原创 从零实现自定义顺序表:万字详解 + 完整源码 + 图文分析

刚入门C++数据结构的你,是不是也遇到过这些头疼的问题?想实现一个能灵活存数据的顺序表,却卡在类结构设计上,不知道该用哪些成员变量;好不容易写了插入、删除接口,却总出现数组越界、数据覆盖的 bug;甚至还没搞懂动态扩容的原理,程序就因为内存泄漏崩溃了……

2025-08-20 12:39:07 1065 16

原创 复杂度分析

时间复杂度分析统计的不是算法运行的时间,运行时间和平台环境也有着很大的关系,这个不是我们能控制的,所以,我们。还有个有趣的知识,假设中国十四亿人口,每个人的省份证号按序排列,找一个人最多需要找多少次?常数阶 < 对数阶 < 线性阶 < 线性对数阶 < 平方阶 < 指数阶 < 阶乘阶。和指数阶相反,对数阶反映“每轮缩减到一半”。平方阶通常出现在嵌套循环中,内外层循环都为。,函数运行时所要的栈帧空间在编译期间已经确定好了,因此。,我们举个例子看一下,假设输入数据大小为。,每轮缩减到原来的一般,循环次数是。

2025-08-19 11:31:20 813 8

原创 初识C++模板

函数模板代表了一个函数家族,函数模板和类型无关,在使用时被参数化,根据实参类型产生特定类型的函数template<typename T1, typename T2,...> 返回值类型 函数名(参数列表){}typename是定义模板参数的关键字// 函数模板template<class T1, class T2,...> class 类模板名{};// 动态顺序表// 注意:Vector不是具体的类,是编译器根据被实例化的类型生成具体类的模具public:, _size(0)

2025-08-17 11:57:26 454 10

原创 C++内存管理

int _a2;int main()// 与C的malloc、realloc、calloc、free不同 new和delete对于自定义类型除了开辟空间还会调用构造和析构free(ptr1);// 内置类型几乎一样free(ptr3);free(ptr5);在申请动态内存空间时,new会调用构造,delete会调用析构new:调用。

2025-08-16 22:45:12 770 7

原创 类和对象收尾

一个类定义在另一个类的内部,这个在类内部的类就称为内部类,内部类是独立的类,仅受类域限制,所以外部类定义的对象中不包含内部类。成员变量和引用成员变量只有一次初始化的机会就是在定义的时候,在初始化列表中,自定义类型成员会调用它的默认构造,而上述演示。,并传参1给构造函数,按照成员变量声明顺序,先初始化。加一,数组在完成n个元素初始化的过程中就完成了计算。实现一个类,计算程序出现多少个类对象。类的边长数组,在类中定义两个静态变量。的构造改成非默认构造就会报错。内部类默认是外部类的友元。,为随机值,后初始化。

2025-08-14 20:49:37 764 9

原创 面试高频考点:传值返回和传引用返回的区别

【核心原则】

2025-07-20 17:33:27 936 7

原创 C++六大默认成员函数

值得一提的是,是我们显⽰写析构函数,对于⾃定义类型成员也会调⽤他的析构,也就是说。

2025-07-17 17:38:46 944 8

原创 初识类和对象

这是类的基本定义,和C语言结构体定义类似,C++中struct也可以定义类,C++兼容C中struct的⽤法,同时struct升级成了类,明显的变化是struct中可以定义函数,⼀般情况下我们还是推荐⽤class定义类再比如:实现一个简单的栈。

2025-07-15 15:28:27 873 4

原创 C语言向C++的过渡

一篇由C语言向C++过渡的知识讲解文章

2025-07-11 20:38:15 995 18

空空如也

空空如也

TA创建的收藏夹 TA关注的收藏夹

TA关注的人

提示
确定要删除当前文章?
取消 删除