leetcode中等31下一个排列

Posted qq_40707462

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了leetcode中等31下一个排列相关的知识,希望对你有一定的参考价值。

在这里插入图片描述错误思路:
我最开始想的是,倒叙遍历,如果最后一个数a[i]的前面,有比他小的数a[j],就把a[i]添加在j的位置,删除a[i],没有的话就接着遍历倒数第二个数

反例:2,3,1->3,1,2
按我的思路就成了3,2,1

正确思路:还需要再把j后面数从小到大排,ij也只需要交换就行,不需要插入再删除

整体思路:
1、我们需要将一个左边的「较小数」与一个右边的「较大数」交换,以能够让当前排列变大,从而得到下一个排列。同时我们要让这个「较小数」尽量靠右,而「较大数」尽可能小。

2、当交换完成后,「较大数」右边的数需要按照升序重新排列。这样可以在保证新排列大于原来排列的情况下,使变大的幅度尽可能小。
3、交换 a[i] 与 a[j],此时可以证明区间[i+1,n) 必为降序。我们可以直接使用双指针反转区间 [i+1,n) 使其变为升序,而无需对该区间进行排序。

class Solution:
    def nextPermutation(self, nums: List[int]) -> None:
        i = len(nums) - 2
        while i >= 0 and nums[i] >= nums[i + 1]:
            i -= 1#左边的较小数,从后往前第一处降序
        if i >= 0:
            j = len(nums) - 1#右边的较大数,找到第一个比nums[i]大的
            while j >= 0 and nums[i] >= nums[j]:
                j -= 1
            nums[i], nums[j] = nums[j], nums[i]
        
        left, right = i + 1, len(nums) - 1
        while left < right:#双双反转
            nums[left], nums[right] = nums[right], nums[left]
            left += 1
            right -= 1

以上是关于leetcode中等31下一个排列的主要内容,如果未能解决你的问题,请参考以下文章

leetcode 406. Queue Reconstruction by Height 根据身高重建队列(中等)

LeetCode 31 Next Permutation(下一个全排列)

精选力扣500题 第32题 LeetCode 31. 下一个排列c++ / java 详细题解

LeetCode:下一个排列31

LeetCode31. 下一个排列

leetcode 46. Permutations 全排列(中等)