• 巧用递归解决煎饼排序问题


    巧用递归解决煎饼排序

    题目:力扣969

    给你一个整数数组 arr ,请使用 煎饼翻转 完成对数组的排序。

    一次煎饼翻转的执行过程如下:

    • 选择一个整数 k ,1 <= k <= arr.length
    • 反转子数组 arr[0…k-1](下标从 0 开始)
      例如,arr = [3,2,1,4] ,选择 k = 3 进行一次煎饼翻转,反转子数组 [3,2,1] ,得到 arr = [1,2,3,4] 。

    数组形式返回使 arr 有序煎饼翻转操作所对应的 k 值序列。任何将数组排序且翻转次数在 10 * arr.length 范围内的有效答案都将被判断为正确。

    示例 1:
    
    输入:[3,2,4,1]
    输出:[4,2,4,3]
    解释:
    我们执行 4 次煎饼翻转,k 值分别为 4,2,4,和 3。
    初始状态 arr = [3, 2, 4, 1]
    第一次翻转后(k = 4):arr = [1, 4, 2, 3]
    第二次翻转后(k = 2):arr = [4, 1, 2, 3]
    第三次翻转后(k = 4):arr = [3, 2, 1, 4]
    第四次翻转后(k = 3):arr = [1, 2, 3, 4],此时已完成排序。 
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    示例 2:
    
    输入:[1,2,3]
    输出:[]
    解释:
    输入已经排序,因此不需要翻转任何内容。
    请注意,其他可能的答案,如 [3,3] ,也将被判断为正确。
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    提示:
    
    1 <= arr.length <= 100
    1 <= arr[i] <= arr.length
    arr 中的所有整数互不相同(即,arr 是从 1 到 arr.length 整数的一个排列)
    
    • 1
    • 2
    • 3
    • 4
    • 5

    思路

    1. 找到最大饼
    2. 将最大的饼放到当前待排序饼中的最下面
    3. 问题域缩小,递归调用 m_sort(arr,n-1)

    如何将最大的饼放在待排序饼中的最下面呢?
    根据题目,我们可以这样做:

    • 先将当前最大的饼放在最上面
      即翻转翻转的是[0,maxpanacakeIndex],即翻转数k = maxpanacakeIndex + 1
    • 再将最上面的饼放在最下面
      即翻转的是[0,n-1] , 即翻转数k = n

    代码

    class Solution {
    public:
    	// 记录翻转操作,即结果集
       vector<int>res;
    
        vector<int> pancakeSort(vector<int>& arr) {        
                 
            m_sort(arr,arr.size());
            return res;
        }
    
        void m_sort(vector<int>& arr,int n){
           // 递归终止条件
            if(n == 1)return;
    		
    		// 记录最大的煎饼
            int maxpancake = -1;
            // 记录最大的煎饼的索引
            int maxpanacakeIndex = -1;
            
            // 找出当前最大的煎饼及其索引
            for(int i = 0 ; i < n; ++i){
                if(arr[i] > maxpancake){
                    maxpancake = arr[i];
                    maxpanacakeIndex = i;
                }
            }
    		
    		// 将最大的煎饼翻转到最上面
            reverse(arr,0,maxpanacakeIndex);
            // 将当前的翻转操作记录到结果集 ,翻转的是[0,maxpanacakeIndex] -> 记录的是maxpanacakeIndex   ======> 等价与题干所说 [0,k-1],翻转k
            res.push_back(maxpanacakeIndex+1);
    		
    		// 将最大的煎饼从最上面翻转到当前待排序并中的最下面(不要误认为是所有饼的最下面)
            reverse(arr,0,n-1);
            // 将当前的翻转操作记录到结果集
            res.push_back(n);
    
            m_sort(arr,n-1);
        }
    
    
        void reverse(vector<int>& arr, int i,int j){         
            while(i < j){
                int m = arr[i];
                arr[i] = arr[j];
                arr[j] = m;
                i++;
                j--;
            }        
        }
    };
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
  • 相关阅读:
    了解Spring的变迁从Spring3到Spring5
    Java8的SerializedLambda详解
    高等教育学:师生关系
    水果店圈子:开个水果店前景如何,现在做水果店行业还赚钱吗
    数据结构——初识数据结构
    无人机航迹规划:七种智能优化算法(DBO、LO、SWO、COA、LSO、KOA、GRO)求解无人机路径规划--提供MATLAB代码
    2023年【道路运输企业安全生产管理人员】考试题库及道路运输企业安全生产管理人员模拟考试题库
    【工作总结】工作为什么总是手忙脚乱
    css三大特性
    草图大师SketchUp Pro 2023
  • 原文地址:https://blog.csdn.net/qq_52399817/article/details/132815812