uva120
这道题目是刘汝佳贪心专题的书上例题。其实总的思路不是太难,但是我们这里主要可以说一下做这个题目的一个基本思路吧,就是他要求我们最后所有的序列从小到大排列,而且给出的操作规则是操作上面的数,不会影响力下面的数,所以我们不妨倒过来思考,就是如果把最大的数字放到了他最后应该放的位置,然后次大的数字要反转的话,是不会影响我们最后的数字的...其实我们仔细思考下,我们循环的数量最多是多少?假设我们有n个数,每一个数从当前的位置首先反转到最上面,然后再反转到他应该在的位置,所以我们的操作最多就是2*n次。
其实做了2年acm,今年青岛打铁过后,再来细细反思以前做过的题目,都是有些为了做题而做题,现在重新拾起来刘汝佳的原因,是感觉自己的基础和很多思路其实没有理得很好,所以开始重新做题写博客,理清思路。
// // Created by 唐律 on 2017/11/15. // #include <stdio.h> #include <algorithm> #include <stdlib.h> using namespace std; const int maxn = 1e3; int loc[maxn],num[maxn],loc1[maxn]; int main() { int i,j,k; while(~scanf("%d", &loc[0])) { int n = 1; loc1[0] = loc[0]; num[loc[0]] = 0; while(1) { if( getchar() != ' ') break; scanf("%d",&loc[n]); loc1[n] = loc[n]; num[loc[n]] = n; n++; } printf("%d",loc[0]); for( i = 1; i < n; i++ ) printf(" %d", loc[i]); printf("\n"); sort(loc,loc+n); for(i = n - 1; i >= 0; i-- ) { int flag = 0; for( k = 0; k < n - 1; k++) if(loc1[k] > loc1[k+1]) { flag = 1; break; } if( flag == 0) break; int temp = loc[i]; while( num[temp] != 0 ) { int now = num[temp];//记录的是当前元素的位置 printf("%d ",n-now); for( j = now; j >= (now+1)/2; j-- ) { swap(loc1[j],loc1[now-j]); num[loc1[j]] = j; num[loc1[now-j]] = now - j; } } printf("%d ",n-i); for( j = i; j >= (i+1)/2; j-- ) { swap(loc1[j],loc1[i-j]); num[loc1[j]] = j; num[loc1[i-j]] = i - j; } flag = 0; for( k = 0; k < n - 1; k++) if(loc1[k] > loc1[k+1]) { flag = 1; break; } if( flag == 0) break; } printf("0\n"); } return 0; }