hdu 1988
地址:http://acm.hdu.edu.cn/showproblem.php?pid=1988
题意:n块煎饼,尺寸分别为1至n,从上到下堆成一堆。正面朝上为+,反面朝上为-。每次可以选择上面若干块整个翻转过来。求翻转的步骤,能使得最后正面朝上,尺寸从上到下是小到大。
mark:没啥困难的,每次选最大的那个经过不超过3次操作翻到最底下。sample给得很好,主要是注意最顶上1的处理就可以了。
代码:
1 # include <stdio.h> 2 3 4 int n, a[35] ; 5 int ans[110], cnt ; 6 7 8 int abs(int x){return x<0?-x:x;} 9 10 11 int find(int x) 12 { 13 int i ; 14 for (i = 1 ; i <= n ; i++) 15 if (abs(a[i]) == x) return i ; 16 return 0 ; 17 } 18 19 20 void reverse(int pos) 21 { 22 int i, j, t ; 23 for (i = 1, j = pos ; i < j ; i++, j--) 24 { 25 t = a[i], a[i] = a[j], a[j] = t ; 26 } 27 for (i = 1 ; i <= pos ; i++) a[i] = -a[i] ; 28 } 29 30 31 void gao() 32 { 33 int i, pos ; 34 cnt = 0 ; 35 for (i = n ; i >= 1 ; i--) 36 { 37 if (a[i] == i) continue ; 38 pos = find(i) ; 39 if (pos != 1) 40 { 41 reverse(pos) ; 42 ans[cnt++] = pos ; 43 } 44 if (a[1] > 0){ 45 ans[cnt++] = 1 ; 46 a[1] = -a[1] ; 47 } 48 if (i != 1) 49 { 50 ans[cnt++] = i ; 51 reverse(i) ; 52 } 53 else{ 54 ans[cnt++] = 1 ; 55 a[i] = -a[i] ; 56 } 57 } 58 } 59 60 61 int main () 62 { 63 int T, nCase = 1, i ; 64 scanf ("%d", &T) ; 65 while (T--) 66 { 67 scanf ("%d", &n) ; 68 for (i = 1 ; i <= n ; i++) 69 scanf ("%d", &a[i]) ; 70 gao() ; 71 printf ("%d %d", nCase++, cnt) ; 72 for (i = 0 ; i < cnt ; i++) 73 { 74 // if (i != 0) printf (" ") ; 75 printf (" %d", ans[i]) ; 76 } 77 puts ("") ; 78 } 79 return 0 ; 80 }