leetcode双指针合集
27. 移除元素
class Solution {public:int removeElement(vector<int>& nums, int val) {/**思路:使用快慢指针,快指针正常往后移动,并将获取的值给慢指针,但是当快指针所指向的值是val的时候慢指针便不再更新;**/ int slowIndex = 0;for(int fastIndex = 0; fastIndex < nums.size(); fastIndex++) {if(nums[fastIndex] != val) {nums[slowIndex] = nums[fastIndex];slowIndex++;}}return slowIndex; }
};
344. 反转字符串
class Solution {public:void reverseString(vector<char>& s) {for(int i = 0,j = s.size()-1; i < s.size()/2; i++,j--) {swap(s[i],s[j]);}}
};
剑指 Offer 05. 替换空格
class Solution {public:string replaceSpace(string s) {/**思路:1.双指针(一个指针指向旧的字符串末尾ptr1,一个指针指向扩容后的字符串末尾ptr2)2.对原字符串的扩容,因为%20是占3个空格的,所以要在原来一个空格基础上进行扩容3.当遇到不是空格的时候,两个指针指向的字符就正常赋值,如果当ptr1指向空格的时候ptr2就前面的3个空格 填上%20*/int count = 0;//记录空格数int oldSize = s.size();for(int i = 0; i < s.size(); i++) {if(s[i] == ' '){count++;}}s.resize(oldSize+2*count);int newSize = s.size();//i和j模拟指针for(int i = oldSize-1,j = newSize-1; i>=0; i--,j--) {if(s[i] == ' '){s[j] = '0';s[j-1] = '2';s[j-2] = '%';j = j-2;}else{s[j] = s[i];} }return s;}
};
151. 翻转字符串里的单词
class Solution {public:/**思路:1.去除空格(字符串前面的空格 字符串中间冗余的空格 字符串后面的空格)2.反转字符串3.将每个单词进行反转**/void removespacing(string &s) {int slowIndex = 0,fastIndex = 0;//定义快慢指针(最终慢指针为去完冗余空格的字符串)//去除字符串前面的空格while(s[fastIndex] == ' '){fastIndex++;}for( ; fastIndex < s.size(); fastIndex++) {//去除冗余的空格if(fastIndex-1 > 0 &&s[fastIndex-1] == s[fastIndex] && s[fastIndex] == ' '){continue;}else {s[slowIndex] = s[fastIndex];slowIndex++;} }//去除末尾的空格(如果字符串的末尾有多个空格的话 上方只能处理到末尾只有一个空格)if(slowIndex-1 > 0 && s[slowIndex - 1] == ' '){s.resize(slowIndex-1);}else{s.resize(slowIndex);}}void reverseStr(string &s,int start,int end){for(int i = start,j = end; i < j; i++,j--) {swap(s[i],s[j]);}}string reverseWords(string s) {removespacing(s);reverseStr(s,0,s.size() - 1);for(int i = 0; i < s.size(); i++) {int j = i;//找到空格while(j < s.size() && s[j] != ' ') {j++;}reverseStr(s,i,j-1);//这里j-1是因为s[j]已经表示的是空格了i = j;}return s;}
};
206. 反转链表
class Solution {public:ListNode* reverseList(ListNode* head) {ListNode* temp;//存放临时结点ListNode* cur = head;ListNode* pre = NULL;while(cur) {temp = cur->next;cur->next = pre;//调转指针pre = cur;//往后移动一个结点cur = temp;}return pre;//当cur指向5的时候 下一个就指向空 那么pre = cur 则就表示前指针表示指向的是5}
};
19. 删除链表的倒数第 N 个结点
class Solution {public:ListNode* removeNthFromEnd(ListNode* head, int n) {/**思路:1.双指针(慢指针p1,快指针p2)2.要删除倒数第n个结点,也就是要正向删除 第(总的节点数 - n)个结点 3.为了处理倒数问题,先让p2往后移动n个结点,(这时候p2还剩下(总的节点数-n = sum)),那么此时p1和p2一块移动,等到p2指向末尾的时候,p1也就指向要删除的结点*/ListNode* fakeNode = new ListNode(0);fakeNode->next = head;ListNode* slowNode = fakeNode;//慢指针ListNode* fastNode = fakeNode;//快指针while(n-- && fastNode != NULL) {fastNode = fastNode->next;}fastNode = fastNode->next;//让其再快一格是为了当快指针到末尾的时候,慢指针指向要删除结点的//的前一个结点 while(fastNode != NULL){fastNode = fastNode->next;slowNode = slowNode->next;}slowNode->next = slowNode->next->next;return fakeNode->next;}
};
18. 四数之和
class Solution {public:vector<vector<int>> fourSum(vector<int>& nums, int target) {vector<vector<int> >ans;vector<int> v;sort(nums.begin(),nums.end());for(int i = 0; i < nums.size(); i++) {if(i > 0 && nums[i-1] == nums[i]) {continue;}for(int j = i+1; j < nums.size(); j++) {if(j-1 > i &&nums[j-1] == nums[j]){//这里的j-1大于i主要考虑的是我们去重复的是从continue; //j开始指向的元素}int left = j+1;int right = nums.size() - 1;while(left < right) {if(nums[i]+nums[j] > target - (nums[left]+nums[right])) right--;else if(nums[i]+nums[j] < target - (nums[left]+nums[right])) left++;else {v.push_back(nums[i]);v.push_back(nums[j]);v.push_back(nums[left]);v.push_back(nums[right]);ans.push_back(v);//去重处理while(left < right && nums[right-1] == nums[right]) right--;while(left > right && nums[left+1] == nums[left]) left++;//换下一组right--;left++;v.clear();}} }}return ans;}
};
15. 三数之和
class Solution {public:vector<vector<int>> threeSum(vector<int>& nums) {/**思路:1.我们将所有元素进行升序处理(这样处理的话,我们可以知道当前面的元素大于0的时候,那么便一定不会出现 a+b+c=0 2.这里我们设置三个指针(模拟的) 第一个指针(i)指向数组的第一个元素,第二个指针(left)指向数组的第二个元素,第三个指针(right)指向数组的最后的元素3.nums[i] + nums[left] + nums[right] > 0; right-- ,i和left不动nums[i] + nums[left] + nums[right] < 0; left++,i和right不动nums[i] + nums[left] + nums[right] = 0;left++,right--,i也移动一个单位当我们找到一组答案的时候,就要同时移动三个指针;因为当我们找到一组答案的时候,如果不移动i,只移动left和right,因为是升序的,那么的话nums[left] + nums[right] 只会更小与nums[i]相加也不会等于0;如果我们想要最终的和为0,那么的话nums[i] < 0,nums[left] < 0,nums[right] > 0,那么往后移动i,如果和为0的话 nums[left] + nums[right]的结果只会更小因此我们每确定一组答案的时候,需要同时移动left,right,i4.这里的去重,我们是当遇到相同的元素跳过它*/vector<vector<int> >ans;vector<int>v;sort(nums.begin(),nums.end());for(int i = 0; i < nums.size(); i++) {if(nums[i] > 0){//如果首元素大于0的话那么就不会有和为0了return ans;}if(i > 0 && nums[i] == nums[i-1]){continue;}int left = i+1;int right = nums.size() - 1;while(left < right) {int sum = nums[i] + nums[left] + nums[right];if(sum > 0) right--;else if(sum < 0) left++;else {v.push_back(nums[i]);v.push_back(nums[left]);v.push_back(nums[right]);ans.push_back(v);//去重处理(相邻的元素出现了重复)while(left < right && nums[right-1] == nums[right]) right--;while(left < right && nums[left+1] == nums[left]) left++;//换下一组答案(上方的去重处理只是指针移动到最后一个重复的元素)right--;left++;v.clear();} }}return ans;}
};
142. 环形链表 II
class Solution {public:ListNode *detectCycle(ListNode *head) {/**思路:1.定义快慢指针(快指针一次移动一个节点,慢指针一次移动两个结点)2.如果有环的话那么的话快慢指针一定会相遇(因为如果没环的话快慢指针永远不相遇)3.那么我们接下来就要确认出口在哪里,(根据以证明的结论,定义一个新的结点头指针指向它,然后快指针和其一块移动,当其相遇的时候,就是出口.**/ListNode* slowNode = head;ListNode* fastNode = head; //当fastNode->next != NULL的时候 是允许fastNode->next->next 为空的//如果没有此条件的话,那么当指针指向最后一个结点的时候,fast->next 已经为空了,它便不能再指向空了//即fast->next->next (不能空指向空)while(fastNode != NULL && fastNode->next != NULL) {fastNode = fastNode->next->next;slowNode = slowNode->next;if(slowNode == fastNode){ListNode* temp1 = fastNode;ListNode* temp2 = head;while( temp1 != temp2) {temp1 = temp1->next;temp2 = temp2->next;}return temp1;} }return NULL;}
};
面试题 02.07. 链表相交
class Solution {public:ListNode *getIntersectionNode(ListNode *headA, ListNode *headB) {/**思路:1.双指针(一个指针指向长链表,一个指针指向短链表)2.我们需要将两个链表右对齐3.将其右对齐的目的是为了让长链表的指针移动到和短链表指针相同的位置这样就可以方便找到相同的指针(只要指针相同那么其接下来的数也相同)4.所以我们需要确定出长链表是谁 */ListNode* node1 = headA;//新定义一个结点方便操作,保存头结点 ListNode* node2 = headB;int lenA = 0;int lenB = 0;while(node1 != NULL) {node1 = node1->next;lenA++;}while(node2 != NULL) {node2 = node2->next;lenB++;} node1 = headA;//上方已经将node1和node2移到最后了node2 = headB;//因为我们需要将长链表的指针进行移动 所以我们需要确定出长链表if(lenB > lenA){swap(lenA,lenB);swap(node1,node2);}int poor = lenA - lenB; //长链表比短链表多的长度while(poor--) {node1 = node1->next;} while(node1 != NULL) {if(node1 == node2) {return node1;}node1 = node1->next;node2 = node2->next;} return NULL;}
};
leetcode双指针合集相关推荐
- LeetCode(合集)括号 golang
LeetCode(合集)括号 20. 有效的括号 golang(三) 22. 括号生成 golang 图解
- LeetCode整理----合集一
一:LeetCode[2] 两个数相加 1:需要考虑进位的问题,需要使用一个变量存储进位标识,每一次都去判断,而且在一个链表判断完成之后,另外一个链表,也是需要单独考虑进位问题的 2:在计算结束后, ...
- LeetCode (合集)合并链表和数组
LeetCode 88. 合并两个有序数组 golang LeetCode 21. 合并两个有序链表 golang 合并两个有序链表并去重 /*** Definition for singly-lin ...
- LeetCode(合集)两数之和总结 (1,167,1346)
1.两数之和 167. 两数之和 II - 输入有序数组 golang 1346. 检查整数及其两倍数是否存在 一个数组是否存在两个数是target的整数倍? 如果有人知道这是LeetCode哪个题, ...
- LeetCode(合集)删除数组中的元素(26,80,283)
26. 删除排序数组中的重复项 80. 删除排序数组中的重复项 II golang 283. 移动零 golang
- LeetCode(合集) 路径总和(二叉树) golang copy的值复制
112. 路径总和 给定一个二叉树和一个目标和,判断该树中是否存在根节点到叶子节点的路径,这条路径上所有节点值相加等于目标和. 说明: 叶子节点是指没有子节点的节点. 示例: 给定如下二叉树,以及目标 ...
- 珍宝鸭的力扣练习(2):指针法的解题合集
题目合集: 题目1:水桶最短板 题目2:目标值寻找 题目3:2数组合并 题目4:第一个不重复的数字 题目5:和为s的两个数字 题目6:倒序打印 快慢指针 题目1:调整数组顺序使奇数位于偶数前面 #双指 ...
- 一些经典的前端文章合集地址
1.2018前端面试总结,看完弄懂, 掘金技术征文 地址 https://juejin.im/post/5b94d8965188255c5a0cdc02#javascript 2.2018上半年掘金微 ...
- 算法基础课【合集1】
文章目录 基础算法 785. 快速排序 786. 第k个数 787. 归并排序 788. 逆序对的数量 789. 数的范围 790. 数的三次方根 791. 高精度加法 792. 高精度减法 793. ...
最新文章
- 2022-2028年中国婴儿用品市场投资分析及前景预测报告
- python获取当前时间的函数_java/python中获取当前系统时间,并与字符串相互转换格式,或者转化成秒数,天数等整数...
- python相关概念
- 【OpenCV3】双线性插值
- 针对C64x+的一些优化经验
- ANTLR教程– Hello Word
- espresso 2.0.4 Apple Xcode 4.4.1 coteditor 价格
- Pytorch 学习笔记:
- 【dfs+简单贪心】Leaf Sets【Codeforces Round #510 (Div. 2)】
- Unity中解析Excel表格工具
- 2021年江西省职业院校技能大赛信息安全管理与评估竞赛样题(高职组)
- c语言使用反三角函数,C语言中反三角函数怎样调用?
- 教你用优化视频的方法提高视频的质量
- linux查看本机IP掩码,linux下 取得本机ip、掩码、网关
- 如何开启Windows远程桌面服务
- 分水岭 matlab代码,分水岭算法MATLAB编程代码解析
- java 实现EME2000(国家大地坐标系)转ECEF坐标系(地心地固坐标系)
- iMac恢复出厂设置及安装
- 阿里云ECS数据迁移到阿里云OSS
- INSERT INTO和INSERT IGNORE INTO 以及REPLACE INTO的区别
热门文章
- mysql实现读写分离
- 【倾情奉献】遥感物候研究:30年长时间序列遥感数据集GIMMS 3g NDVI产品预处理完整步骤
- Envi和ArcGIS软件打开和处理.NC4数据
- Android之实现首尾带圆角的多颜色水平条
- C语言之理解(*(void (*)())0)()和signal函数
- realloc函数使用总结
- *p++,(*p)++,*++p,++*p有什么不同
- python桌面程序开发_程序员之路:python3+PyQt5+pycharm桌面GUI开发
- @order注解_别再用ifelse了,用注解去代替他吧
- 老师“鬼话”全曝光!哈哈哈哈哈全国的老师都这样吗?