2:变量设置和数据结构
===========
经过上述分析我们不拿发现,调用Arrays类中的排序方法,有手就行。
关键是如何将排序后的数组筛选变的只有不重复元素
从而筛选后的数组长度==糖果总数。
这时候相信有些老铁就联想到了力扣
力扣中这个入门题,删除重复元素
我们直接调用快慢指针。
为什么强调他是快慢指针而不是双指针呢?
因为盯着两个指针一起走,考虑两个指针的情况
像个智障,不断地排除BUG情况,凑出来的代码勉强排除特殊情况,可以通过
上面的题力扣
例如我的第一次提交:
package leetcode.review.rereview;
/*
@author 作者 E-mail:
@version 创建时间:2021年10月31日 下午12:12:31
类说明:removeDuplicates 原地删除数组的多余元素
给你一个有序数组 nums ,请你 原地 删除重复出现的元素,使每个元素 只出现一次 ,返回删除后数组的新长度。
不要使用额外的数组空间,你必须在 原地 修改输入数组 并在使用 O(1) 额外空间的条件下完成。
*/
public class RemoveDuplicates
{
public int removeDuplicates(int[] nums)
{
if(nums.length<=1)
{
return nums.length;//对长度0和1的数组进行处理
}
int flag=nums[0];
int slow=0;
int fast=0;
for(;fast<nums.length;fast++)
{
if(nums[fast]==flag)
{
fast++;
{
if(fast==nums.length)
{
break;
}
}
}
if(nums[fast]!=flag)
{
slow++;
flag=nums[fast];
nums[slow]=nums[fast];
}
}
return slow+1;
}
}
/*
此题我的编程思想从想法上来说还是很成熟的,风骚的双指针,快慢指针,当他等于前边已有的元素时直接fast++跳过他,
跳过之后再看下一个是否也还是跟旗帜相同,for循环和内置的fast++推动继续前进。当快指针指到不等于旗帜的数据时,交换,换位,对慢指针进行操作。但是需要考虑,当快指针指向边界并且这一整个数组都是同一个数字,如【1,1,1,1】时,会边界溢出。
计算机是非常精密和严格的。
同时需要对空数组,只有一个的数组进行特殊情况处理
其中【1,1】这种特殊情况,全是1,但是返回长度还是0,且根据程序编写的巧合性,第一次相等于flasg
fast++之后,他会返回for再执行语句三fast++,这时候fast就进不来了!
*/
//[1,1,2]
//[0,0,1,1,1,2,2,3,3,4]
//[0,0,1,1,1,2,2,3,3,4,55,55,66]
//[]
//[1]
//[1,2]
//[1,2]
//[1,1,1]
//执行出错信息:
//java.lang.ArrayIndexOutOfBoundsException: Index 3 out of bounds for length 3
// at line 19, Solution.removeDuplicates
// at line 54, DriverSolution.helper
// at line 84, Driver.main
//最后执行的输入:
//[1,1,1]
14点01分
从2021.10.31日 12点开始
第一题是删除重复元素
盯着两个指针一起走
像个智障,不断地排除BUG情况,凑出来的
并且把这种错误思想引入了今天做的第二题移动零
其实没必要盯着两个指针
现针对第一题重做!
package leetcode.daily;
/*
@author 作者 E-mail:
@version 创建时间:2021年10月31日 下午2:03:47
类说明:第十四天,对本日做的第一题重做。
*/
public class Daily13_1_2
{
public int solution(int[] nums)
{
if(nums.length<2)
{
return nums.length;
}
int slow=0;
int fast=0;
int flag=nums[0];
while(fast<nums.length)
{
if(nums[fast]==flag)
{
fast++;
//此处还要加,防止fast出界
{if(fast==nums.length) break;}
}
if(nums[fast]!=flag)
{
nums[slow++]=nums[fast];
flag=nums[fast];
}
}
return slow+1;
}
}
class Solution
{
public int removeDuplicates(int[] nums)
{
if(nums.length<2)
{
return nums.length;
}
int slow=1;
int fast=0;
int flag=nums[0];
for(;fast<nums.length;fast++)
{
if(nums[fast]!=flag)
{
nums[slow++]=nums[fast];
flag=nums[fast];
}
}
return slow;
}
}
双指针里for和while是一样的,记住模板稍加更改就可
这样我们通过刷题整理得到了双指针的框架:,
双指针,一左一右:left||right
快慢指针,一快一慢:slow和fast
两种循环方式:
while和for 其中用while时,
需要在循环内对fast(right)指针自加
for循环中(依赖for自加即可)
所需要空间为原数组
3:代码求解:
=======
class Solution
{
public int distributeCandies(int[] candyType)
{
int bornlen=candyType.length;
if(bornlen==2)
{
return 1;
}
Arrays.parallelSort(candyType);
int left=1;
int right=0;
int flag=candyType[0];
for(;right<bornlen;right++)
{
if(candyType[right]!=flag)
{
flag=candyType[right];
candyType[left++]=candyType[right];
}
}
if(left>bornlen/2)
{
return bornlen/2;
}
return left;
}
}
4:快慢指针总结:
=========
为何叫做快慢指针,而不叫双指针
因为如
#977 有序数组的平方 |
这种题,用到的双指针,一左一右,两个一个在数组0位置,一个在数组末尾,需要同时盯两个
指针力扣
但是本题,快慢指针一起从头开始,盯着一个即可
for(int right=0;right<数组名.length;fast++)
{
if(不满足条件)
{
看题目要求执不执行操作
//如果是while循环,此处fast应该自加,推动fast快指针去检查下一个位置
自我介绍一下,小编13年上海交大毕业,曾经在小公司待过,也去过华为、OPPO等大厂,18年进入阿里一直到现在。
深知大多数前端工程师,想要提升技能,往往是自己摸索成长或者是报班学习,但对于培训机构动则几千的学费,着实压力不小。自己不成体系的自学效果低效又漫长,而且极易碰到天花板技术停滞不前!
因此收集整理了一份《2024年Web前端开发全套学习资料》,初衷也很简单,就是希望能够帮助到想自学提升又不知道该从何学起的朋友,同时减轻大家的负担。
既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,基本涵盖了95%以上前端开发知识点,真正体系化!
由于文件比较大,这里只是将部分目录截图出来,每个节点里面都包含大厂面经、学习笔记、源码讲义、实战项目、讲解视频,并且会持续更新!
如果你觉得这些内容对你有帮助,可以扫码获取!!(备注:前端)
更多面试题
**《350页前端校招面试题精编解析大全》**内容大纲主要包括 HTML,CSS,前端基础,前端核心,前端进阶,移动端开发,计算机基础,算法与数据结构,项目,职业发展等等
SPtHeH5J-1713731509754)]
[外链图片转存中…(img-SOie3P0V-1713731509754)]
既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,基本涵盖了95%以上前端开发知识点,真正体系化!
[外链图片转存中…(img-cDynIwmm-1713731509755)]
由于文件比较大,这里只是将部分目录截图出来,每个节点里面都包含大厂面经、学习笔记、源码讲义、实战项目、讲解视频,并且会持续更新!
如果你觉得这些内容对你有帮助,可以扫码获取!!(备注:前端)
[外链图片转存中…(img-JO5SzKN3-1713731509755)]
更多面试题
**《350页前端校招面试题精编解析大全》**内容大纲主要包括 HTML,CSS,前端基础,前端核心,前端进阶,移动端开发,计算机基础,算法与数据结构,项目,职业发展等等
[外链图片转存中…(img-7RYMEwmt-1713731509756)]