首先我们来看题目:
我们就以【1,0,-1,0,-2,2】
- 我们首先排除长度等于0和排除长度小于4的列表,没有4个数相加,达不到题目要求自然返回【】
- 给nums进行排序,准备依次取值。排序之后【-2,-1,0,0,1,2】
- 循环第一层到len(nums)-3即可,对应第一个0的地方,因为最后可以取到【0,0,1,2】就可以结束了,剩下三个直接省略,节省空间。
- 我们给循环的i值进行判断,首先如果1>0并且nums[i]=nums[i-1]说明循环i值重复了,则直接跳过,我们这里介绍continue这个是表示跳出本次循环。还有就是如果nums[i]+nums[i+1]+nums[i+2]+nums[i+3]>target,说明了最小的一组组合都比目标值大,那么就没有循环的意义了,直接退出。最后如果nums[i]+nums[len(nums-3)]+nums[len(nums)-2]+nums[len(nums)-1]<target,这个时候说明了nums[i]和当前最大的三个数相加都比target小,那么直接跳出本次循环,让i进入下次,变得更大。
- 定义第二次循环,对于第二次循环应该处于i+1—len(nums)-2之间,因为要保证比i大1的范围,对j进行条件判断,同上,有重复则跳出,如果nums[i]+nums[j]+nums[j+1]+nums[j+2]>target,那么break,如果nums[i]+nums[j]+nums[len(nums)-2]+nums[len(nums)-1]<target,那么continue.
- 定义指针,L=j+1,R=len(nums)-1,左右指针定义完毕之后,while L<R:
- total=nums[i]+nums[j]+nums[L]+nums[R]进入判断,如果total=target,则进行添加,并且判断nums[L]是否有重复,如果有则L+1,如果没有同样L+1。判断nums[R]是否有重复,如果有则R-1,如果没有同样R-1.
- 如果total<target,说明左指针太小了,需要增加,L+1
- 如果total>target,说明右指针太大了,需要减少,R-1
- 最后返回添加的list列表,大功告成!!!
看代码
nums=[1,0,-1,0,-2,2]
target=0
final_list=[]
if len(nums)==0 or len(nums)<4:
return final_list
nums.sort()
for i in range(len(nums)-3):
if i>0 and nums[i]==nums[i-1]:
continue
if nums[i]+nums[i+1]+nums[i+2]+nums[i+3]>target:
break
if nums[i]+nums[len(nums)-3]+nums[len(nums)-2]+nums[len(nums)-1]<target:
continue
for j in range(i+1,len(nums)-2):
if j>i+1 and nums[j]==nums[j-1]:
continue
if nums[i]+nums[j]+nums[j+1]+nums[j+2]>target:
break
if nums[i]+nums[j]+nums[len(nums)-2]+nums[len(nums)-1]<target:
continue
L=j+1
R=len(nums)-1
while L<R:
total=nums[i]+nums[j]+nums[L]+nums[R]
if total==target:
final_list.append([nums[i],nums[j],nums[L],nums[R]])
while L<R and nums[L]==nums[L+1]:
L=L+1
L=L+1
while L<R and nums[R]==nums[R-1]:
R=R-1
R=R-1
elif total<target:
L=L+1
else:
R=R-1
return final_list
请有不明白的跟我上方描述一一对应,彻底把双指针弄明白,感谢各位大佬的观看,谢谢大家!!