969. Pancake Sorting
问题:
给定数组,
假定反转动作k,表示:将数组前k个元素进行反转。
求反转动作k的序列,使得数组最终成为一个递增数组。(特:该数组为1~A.size()的一个排序)
Example 1: Input: [3,2,4,1] Output: [4,2,4,3] Explanation: We perform 4 pancake flips, with k values 4, 2, 4, and 3. Starting state: A = [3, 2, 4, 1] After 1st flip (k=4): A = [1, 4, 2, 3] After 2nd flip (k=2): A = [4, 1, 2, 3] After 3rd flip (k=4): A = [3, 2, 1, 4] After 4th flip (k=3): A = [1, 2, 3, 4], which is sorted. Example 2: Input: [1,2,3] Output: [] Explanation: The input is already sorted, so there is no need to flip anything. Note that other answers, such as [3, 3], would also be accepted. Note: 1 <= A.length <= 100 A[i] is a permutation of [1, 2, ..., A.length]
解法:
反转方法:
找到下一个最大的数nextmax的index:i
首先将这个数反转到开头,即A[0]的位置:即需要反转的k=i
然后将这个数反转到下一个最大位置nextmax-1:即需要反转的k=nextmax-1
这里要用到c++的反转数组函数reverse(A.begin(),A.end())->reverse(反转开头位置,反转结束位置+1)
因此,我们做一个元素的定位需要反转以下2次:
reverse(A.begin(),i+1);
reverse(A.begin(),nextmax);
代码参考:
1 class Solution { 2 public: 3 vector<int> pancakeSort(vector<int>& A) { 4 int i; 5 int nextmax; 6 vector<int> res; 7 for(nextmax=A.size(); nextmax>0; nextmax--){ 8 for(i=0; A[i]!=nextmax; i++); 9 if(i+1==nextmax) continue;//省略正反反转数相同的 10 reverse(A.begin(), A.begin()+i+1); 11 res.push_back(i+1); 12 reverse(A.begin(), A.begin()+nextmax); 13 res.push_back(nextmax); 14 } 15 return res; 16 } 17 };
递归实现:recuration
1 class Solution { 2 public: 3 vector<int> res; 4 vector<int> pancakeSort(vector<int>& arr) { 5 int n=arr.size(); 6 pancakesort(arr, n); 7 return res; 8 } 9 void pancakesort(vector<int>& arr, int n) { 10 if(n==1) return; 11 int i=0; 12 for(i=0; arr[i]!=n; i++);//find maxvalue:arr[i] 13 //flip maxvalue to the top[0]: reverse:0~maxvalue 14 if(i!=n-1) {//maxvalue is already at the bottom. then skip reverse operation. 15 cout<<i<<endl; 16 reverse(arr.begin(), arr.begin()+i+1); 17 res.push_back(i+1); 18 //flip top[0]->end: reverse:0~end 19 reverse(arr.begin(), arr.begin()+n); 20 res.push_back(n); 21 } 22 pancakesort(arr, n-1); 23 } 24 };