自定义博客皮肤VIP专享

*博客头图:

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

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

博客底图:

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

栏目图:

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

主标题颜色:

RGB颜色,例如:#AFAFAF

Hover:

RGB颜色,例如:#AFAFAF

副标题颜色:

RGB颜色,例如:#AFAFAF

自定义博客皮肤

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

原创 CMU15445 (Fall 2023) Project2 - EXTENDIBLE HASH INDEX 思路分享

如果你对文章的某些描述感到疑惑,或是发现了文章的错误,欢迎在评论区提出: )

2024-08-08 20:02:25 1180 3

原创 CMU15445 (Fall 2023) Project 1 - Buffer Pool 思路分享

操作系统为应用程序提供了默认的缓存机制,DBMS作为应用程序,为什么不使用默认的缓存机制呢?因为DBMS需要对数据进行(1)空间控制:将经常使用的page写入到磁盘的连续位置,预读取page, (2)时间控制:何时将数据写回磁盘,何时读取数据到内存,使得磁盘I/O次数最少。为此,DBMS需要高度定制缓存策略。在Project 1中,你需要实现DBMS的缓存池模块(Buffer Pool Manager),定制缓存策略,负责管理数据在磁盘和内存之间的流动。

2024-08-07 21:11:18 689

原创 CMU15445 (Fall 2023) Project 4 - Concurrency Control 思路分享

Project 4需要我们为数据库实现MVOCC, 也就是基于时间戳的多版本并发控制(OCC + MVCC). 这是一种乐观的控制并发的手段,其原理类似CAS(Compare and Swap). 只不过在compare失败时,事务将被回滚。2023 Fall的PJ 1大概有240人完成,最后的PJ 4只有不到160人完成,我没算错的话,少了三分之一的人: ( “行百里者半九十”,希望各位读者能有始有终,坚持到最后捏: )如果你对文章的某些描述感到疑惑,或是发现了文章的错误,欢迎在评论区提出: )

2024-08-06 20:16:34 1024

原创 CMU15445 (Fall 2023) Project 3 - Query Execution 思路分享

在Project 3中,我们将实现数据库的查询执行部分。不同算子的具体执行逻辑编写优化规则,转换查询计划,以提高其执行效率相比于Projcet 2,本次项目侧重于源码阅读,我们需要看懂BusTub的查询执行逻辑,弄清楚每个组件之间的关系,否则我们将无从下手。此外,ButTub提供了Live Shell,我们可以在网页上运行SQL,或是用来debug。

2024-08-04 18:50:36 1163 7

原创 45. 跳跃游戏 II && 763. 划分字母区间(LeetCode热题100)

用l,r区间维护当前能跳跃的区间,计算当前区间能跳跃到的最右区间,以此更新r。当r >= len(nums) - 1就可以返回了。本质是合并区间,记录每个字符最后一次出现位置last。试图扩大l,r区间(初始为0,0),若。说明无法扩大区间,维护ans。从左往右遍历s,根据。

2024-07-21 11:00:00 227

原创 121. 买卖股票的最佳时机 && 55. 跳跃游戏(LeetCode热题100)

从左到右维护能跳到的最右区间,当最右区间大于等于最后一个下标时,返回true。统计前i天最小的买入价格时,计算在第i天卖出是否能得到最大利润。

2024-07-20 10:00:00 314

原创 215. 数组中的第K个最大元素 && 347. 前 K 个高频元素(LeetCode热题100)

写个快排,使数组升序,返回倒数第k个元素即可。统计每个元素的出现次数,按照出现次数排序即可。

2024-07-19 19:50:58 291

原创 394. 字符串解码 && 739. 每日温度(LeetCode热题100)

遍历数组,将元素与下标push进栈,如果当前元素大于栈顶元素,出栈直到当前元素小于栈顶元素,维护ans数组,ans[出栈元素的下标] = 当前元素下标 - 出栈元素下标。如果最后有剩余元素,这些元素的ans为0。curr_str:遍历整个字符串时。

2024-07-12 14:21:56 376

原创 每日两题 / 20. 有效的括号 && 155. 最小栈(LeetCode热题100)

根据栈的先进后出性质,push一个数后,如果该数大于最小数,那么之后获取的最小数一定不是该数,所以无需额外记录该大数的信息。向辅助栈push当前最小数(辅助栈的栈顶)如果该数小于最小数,那么之后获取的最小数就是该数,需要额外记录该数的信息。向辅助栈push该数。的时间找出最小数,一定需要额外的空间保存信息,这里使用一个辅助栈维护额外的信息。遇到右括号判断栈顶是否为匹配的左括号。pop操作时,同时pop两个栈的栈顶。

2024-07-03 16:36:05 447

原创 每日两题 / 34. 在排序数组中查找元素的第一个和最后一个位置 && 33. 搜索旋转排序数组(LeetCode热题100)

34. 在排序数组中查找元素的第一个和最后一个位置 - 力扣(LeetCode)根据二分函数,得到>=target和<=target的两个,分别是答案的l和rclass Solution {public: vector<int> searchRange(vector<int>& nums, int target) { if (nums.size() == 0) return { -1, -1 }; vector&lt

2024-06-03 17:07:22 547

原创 每日两题 / 198. 打家劫舍 && 74. 搜索二维矩阵(LeetCode热题100)

如果当前行的第一个元素小于等于target并且下一行的第一个元素大于target,那么target只可能存在与当前行。表示考虑前i + 1号房屋,能获取的最大金额。对于没一间房屋都有偷与不偷两种选择。我们需要从两种选择中,取最大值。转移,因为不能偷窃相邻房屋,转移,此时可以偷窃相邻房屋。

2024-06-03 16:31:02 523

原创 每日两题 / 131. 分割回文串 && 42. 接雨水(LeetCode热题100)

数据量较小,考虑直接暴力,每次dfs:以bg作为左区间,往右遍历,找到一段回文串区间后,将回文串插入。第i个位置的雨水高度为:左边最高柱子与右边最高柱子的最小值。,并以下一个下标为bg,再次进行dfs,dfs后记得回溯。先预处理左右两边的最高柱子高度,然后线性遍历一遍即可。

2024-05-28 16:56:31 336

原创 每日两题 / 79. 单词搜索 && 39. 组合总和(LeetCode热题100)

每次dfs时,往四个方向走,若当前字符不匹配则回溯,记得消除访问数组对应的标记。遍历board,遇到字符等于word的第一个字符时,进行dfs回溯。中,从左往右选择一个数,并更新bg为这个数所在的下标。设置访问数组,标记已经走过的坐标。若bg总是为0,将出现重复的组合。

2024-05-26 16:53:40 360

原创 每日两题 / 207. 课程表 && 208. 实现 Trie (前缀树)(LeetCode热题100)

有向图判环,使用拓扑排序即可。

2024-05-21 17:17:57 430

原创 每日两题 / 994. 腐烂的橘子 && 200. 岛屿数量(LeetCode热题100)

可以将ans初始化为-1,特判:当没有烂橘子时(层数为0),答案不再是0-1,而是0。做一遍bfs即可,记录bfs最后的层数,答案就是层数-1。遍历整个数组,遇到’1’则进行一次bfs,bfs整个岛屿。

2024-05-16 17:33:27 402

原创 每日两题 / 236. 二叉树的最近公共祖先 && 124. 二叉树中的最大路径和(LeetCode热题100)

每次递归判断:以当前节点为起点的最长路径,需要先判断以左右子节点为根节点的最长路径(可能为0,表示路径中没有节点),然后加上当前节点值。dfs统计根节点到p,q节点的路径,两条路径中最后一个相同节点就是公共祖先。同时维护“经过当前节点的最长路径”

2024-05-15 16:48:37 242

原创 每日两题 / 437. 路径总和 III && 105. 从前序与中序遍历序列构造二叉树(LeetCode热题100)

假设当前路径和为cur,那么ans += 路径和(cur - target)的出现次数。前序遍历时,维护当前路径(根节点开始)的路径和,同时记录路径上每个节点的路径和。在前序遍历中,分别确定左右子树节点的范围,两者的第一个节点就是根节点的左右节点。根节点的左右子节点如何构造?根据中序遍历中,根节点的位置确定左右子树节点数量。递归构造,每次构造子树的根节点。

2024-05-14 21:56:51 234

原创 每日两题 / 199. 二叉树的右视图 && 114. 二叉树展开为链表(LeetCode热题100)

若右指针不为空,我们则需要先使右指针指向的节点满足题目的条件。思考方向就变成了:从先序遍历的最后一个节点开始,往回维护。因为最后一个节点的右指针一定为空,此时保存该节点的地址。接着遍历倒数第二个节点,将倒数第二个节点的右指针指向它。然后思考方向就变成了:怎样的遍历方向是倒着的先序遍历?我们需要修改当前节点的右指针为先序遍历的下一个节点。先走右指针再走左指针的后序遍历,就是倒着的先序遍历。层序遍历二叉树,保存每一层的最后一个值即可。

2024-05-13 16:48:40 255

原创 每日两题 / 108. 将有序数组转换为二叉搜索树 && 543. 二叉树的直径(LeetCode热题100)

先选择整个数组的中点作为根节点,然后选择对半分后的两个子数组的中点作为根节点的左右节点…直径可以理解为:左节点的最大深度+右节点的最大深度。每次将数组对半分,数组的中点作为树的节点。搜索树中所有节点的直径,找到最大的即可。

2024-05-12 17:13:51 413

原创 每日两题 / 101. 对称二叉树 && 230. 二叉搜索树中第K小的元素(LeetCode热题100)

每次遍历时,一个指针向左,另一个就要向右。一个向右,另一个就要向左。利用二叉搜索树的中序遍历,得到的序列是有序的这一性质。当中序遍历到第k个数时,将其返回即可。用两个指针同时遍历树的左右子树即可。

2024-05-11 16:48:42 373

原创 每日两题 / 226. 翻转二叉树 && 98. 验证二叉搜索树(LeetCode热题100)

或者当实现函数dfs(TreeNode *cur, long long l, long long r)保证当前节点的值在[l, r]区间内即可,每次dfs都需要用当前节点的值更新区间。以后续遍历的方式交换当前节点的左右指针。中序遍历得到的序列有序。

2024-05-10 16:27:37 267

原创 每日两题 / 104. 二叉树的最大深度 && 102. 二叉树的层序遍历(LeetCode热题100)

递归判断,当前节点的最大深度为1 + max(左节点的最大深度,右节点的最大深度)使用队列,每次出队前先记录当前队列的长度k,k为层的节点数量。此时只需要将前k个节点出队并将节点的左右子节点入队即可。在出队的同时维护答案。

2024-05-09 15:07:14 351

原创 每日两题 / 23. 合并 K 个升序链表 && 94. 二叉树的中序遍历(LeetCode热题100)

若lists有k个元素,调用k - 1次(两个有序链表的合并)即可。使用栈模拟递归调用的过程。

2024-05-09 09:02:11 209

原创 每日两题 / 138. 随机链表的复制 && 148. 排序链表(LeetCode热题100)

将链表转换成数组,sort后再转换成链表。用哈希表记录原链表中的节点是否被复制过。遍历原链表并通过哈希表维护新链表。

2024-05-07 16:32:24 399

原创 每日两题 / 24. 两两交换链表中的节点 && 25. K 个一组翻转链表(LeetCode热题100)

对于每组节点的翻转,使用三个指针,将pre->cur修改cur->pre,再用next更新两个指针(pre = cur,cur = next)定义三个指针,交换前先保存ntnt指针为next->next,cur和next两个节点,然后将pre->next指向next。若pre为空,说明当前交换的节点为头两个节点,不需要修改pre->next。最后,若k不能整除n,那么将上一组节点的尾节点next指向剩下节点的头节点。翻转完一组节点,将尾节点的next指向刚才翻转一组节点的头节点。

2024-05-06 22:36:04 340

原创 每日两题 / 2. 两数相加 && 19. 删除链表的倒数第 N 个结点(LeetCode热题100)

需要维护当前节点的pre节点,以及head指针的引用:要删除的节点是第一个节点时,直接修改head指针。高精度加法,用vector保存两个操作数,进行高精度加法后,将保存结果的vector转换成链表即可。类似后序遍历,dfs记录当前节点是倒数第几个节点。

2024-05-05 11:32:49 287

原创 每日两题 / 234. 回文链表 && 21. 合并两个有序链表(LeetCode热题100)

cur1指向list1第二个节点,pre1指向第一个,cur2指向list2第一个节点。若最后cur2不为空,说明list2的节点还没有插入到list1,插入剩余节点即可。保证list1的首元素小于list2首元素,然后将list2插入到list1。dfs到最后一个节点,开始与第一个节点进行比较。先创建一个指针指向第一个节点。

2024-04-27 16:23:18 408 1

原创 每日两题 / 78. 子集 && 17. 电话号码的字母组合(LeetCode热题100)

通过二进制数的方式,若第k位为1,表示最终的集合中存在nums[k]当答案长度等于digits的长度,将可能的答案保存。先建立数字与字符串之间的映射,接着dfs每个数字。每次取数字对应字符串中的一个字符加入可能的答案。只要遍历所有可能的二进制数即可。

2024-04-26 15:51:15 443

原创 每日两题 / 240. 搜索二维矩阵 II && 48. 旋转图像 - 力扣(LeetCode热题100)

从右上角开始搜索,若当前值大于target,向左走,因为当前列的所有值都大于target。加上每次向一个方向移动k个曼哈顿距离,但是移动后的坐标“出界”,此时就要向另一个方向调整。若当前值小于target,则当前行向左的所有值小于target,向下走。每次完成一层中4个数的位置交换,如何得到这4个数的坐标?讲一个符合我直觉的解法:从外向内,一层层地旋转。每次坐标的变化,方向都是固定的:右下左上。将出界的曼哈顿距离加到另一个方向上。并且每次的曼哈顿距离都是相同的。

2024-04-25 21:40:53 321

原创 每日两题 / 46. 全排列 && 41. 缺失的第一个正数(LeetCode热题100)

若是出现了,将其乘以-1(如果是正数),而数组中原本就存在负数,这些负数不影响答案,将它们先设置为n + 1。否则将(该数的值 - 1)作为数组下标,将该位置上的数置为负数。最后从头开始遍历数组,出现的第一个正数的(下标+1)则为答案。题目要求使用常数空间解决问题,也就是可以使用题目传入的数组。接着遍历整个数组,对于每个数取绝对值,若该数>n,则跳过。利用数组下标记录值为(值为数组下标+1)的数是否出现过。当选择了n个数时,将已经选择的数加入答案。若数组长度为n,那么答案最多为n + 1。

2024-04-25 11:35:46 285

原创 每日两题 / 438. 找到字符串中所有字母异位词 && 238. 除自身以外数组的乘积(LeetCode热题100)

由于用nums作为前缀和数组,ans作为后缀和数组,即可达到空间复杂度为。维护与p串等长的滑动窗口,记录其中每个字符的出现次数。每次滑动后将当前次数与p串的次数比较即可。维护"前缀和"与"后缀和"数组即可。记录p串每个字符出现次数。

2024-04-22 17:29:21 338

原创 每日两题 / 53. 最大子数组和 && 56. 合并区间(LeetCode热题100)

以nums[i]结尾的子数组只有两种情况,子数组只有nums[i]一个元素、子数组不止nums[i]一个元素。经典dp题,dp[i]表示以nums[i]为结尾的所有子数组中,最大的和。若遇到右边界小于左边界的情况,说明出现不重叠区间,此时维护答案。按左端点排序,遍历区间,记录一开始的作曲兼并维护最大的右边界。将i从左到右遍历,考虑dp[i]如何维护?在两种情况中,取最大值即可。

2024-04-18 22:10:26 262

原创 每日两题 / 189. 轮转数组 && 560. 和为 K 的子数组(LeetCode热题100)

考虑直接将元素向后移动k位,因为移动覆盖将导致数据丢失,所以我们需要将“即将被覆盖的数据”保存起来。k %= 数组长度,数组长度 / k + 1就是需要移动的次数。若当前的前缀和为pre,则ans += mp[pre - k]将整个数组反转,再分别反转前k个元素和剩下的元素即可。前缀和+查找,用mp记录每个位置上的前缀和出现了几次。需要注意的是,0个元素的前缀和为0。向右轮转将使尾部k个元素顶到头部。对前k - 1个数进行移动即可。

2024-04-17 18:21:26 260

原创 每日两题 / 76. 最小覆盖子串 && 239. 滑动窗口最大值(LeetCode热题100)

类似双指针(滑动窗口),一开始l和r指向0下标,当区间。之间的字符串无法覆盖t串时,r++。用大堆维护窗口中的k个数,同时维护这些数在数组中的下标。就是一个满足题意的区间,根据该区间大小维护答案即可。当堆顶元素的下标小于窗口的左边界时,删除堆顶元素。或者使用单调队列,每次移动后,取队头元素即可。,如果该区间能覆盖t串,那么l++。接着移动l指针,假设当前区间为。

2024-04-17 18:00:44 204

原创 每日两题 / 15. 三数之和 && 73. 矩阵置零(LeetCode热题100)

最后,左指针不能从数组的0下标开始,应该从t的后一位开始。直接将原数组的第0行的第0列作为这两个数组,此时直接修改第0行/第0列的元素为0不会影响答案。用两个数组维护哪些行/哪些列出现了0,如果第i行/列出现了0,将第i个元素置0。根据题目要求,确定两数之和为目标值后,两个指针都需要跳过相同的数,才能继续走。问题是:需要确定第0行/第0列是否已经存在0,若存在则需要将整行/整列置0。先排序,左右两个指针,指向的数之和大于目标值,则r–,反之l++先确定一个数t,对于剩下的两个数,要求两数之和为t的负数。

2024-04-16 17:38:48 586

原创 每日两题 / 22. 括号生成 & 54. 螺旋矩阵(LeetCode热题100)

遍历方向为右下左上,根据该方向定义dx,dy方向数组。遍历时保存记录,遇到访问过的或者越界,则需要替换方向。dfs生成合法的括号序列即可。

2024-04-15 14:44:48 280

原创 每日两题 / 142. 环形链表 II & 146. LRU 缓存(LeetCode热题100)

对于最近访问的元素,若不在链表中,则创建新节点并插入链表头(添加),若在链表中,则将其移动到链表头(删除+增加)。综上,我们的链表需要(增加+删除)这两个操作,显然使用双向链表更优。越靠近链表的头指针,越经常访问该元素。越靠近首元素/尾元素,越经常访问该元素?维护访问顺序时,对于数组,需要。显然链表无法作用,所以使用哈希表作为辅助结构,存储key值与其在链表中的位置(节点地址)问题是题目要求:哈希表容量有限,超出容量时,将删除最久未访问的kv。地修改节点,显然链表在时间上更优且满足题意。

2024-04-12 21:12:33 1133

原创 每日两题 / 3. 无重复字符的最长子串 & 84. 柱状图中最大的矩形(LeetCode热题100)

解题的关键在于最小的柱子,对所有柱子进行排序,假设当前柱子的高度为h,则不用考虑高度大于h的柱子,考虑高度小于h的柱子。那么能勾勒的最大矩形为,以:向左第一个小于h的柱子与向右第一个小于h的柱子为底,高为h的矩形。移动r,若新加入的字符和已有字符重复,则不断移动l,直到l和r之间不出现重复字符。双指针,l和r从字符串最左边开始,保存l和r之间的所有字符。每次移动完r并保证l和r之间无重复字符,则维护ans。注意:移动的过程中需要维护l和r之间的字符。从最小高度开始查找最大矩形,即可。

2024-04-12 11:17:34 359

原创 每日三题 / 128.最长连续序列 & 283.移动零 & 11.盛最多水的容器(LeetCode热题100)

设置左右指针,每次移动数值较小的指针。因为此时,对于较小值来说,此时已经达到最优解。若移动数值较大指针,底面积将减小,而高度不变(由较小值决定),不可能出现更优解。对于数组中连续序列的第一个数,设置cnt初始为1,根据unordered_set查找该连续序列的长度。而对于较大值来说,虽然底面积减小,但可能遇到比较小值大的值,出现更优解,直到自己成为较小值。统计0的数量,遇到非0元素,将当前元素向前移动(0的数量)最后将数组的后(0的数量)个元素,修改为0即可。只需在每次移动后,维护较大值即可。

2024-04-10 11:42:59 326

原创 每日两题 / 1.两数之和 & 49.字母异位词分组(LeetCode热题100)

解法:将所有数排序,并记录这些数的下标,双指针从左右向中间走。指向的两数相加大于target则r–,小于则l++,第一对相等的数即为答案。可以确定的是,将所有单词中的字符升序排序后,将出现多个相同单词,这些单词作为“字母异位词”分为一组。贴双指针解法,证明很简单:思考为什么双指针不会移动到两个答案之间?对于每个单词,将其升序排序,用map记录该单词所位于的组号,若无记录,则作为新组。当然,用二分、哈希也是可以的,不过时间复杂度为。若单词重新排列后,和某个单词相同,则分为一组。

2024-04-09 17:03:01 738

空空如也

空空如也

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

TA关注的人

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