吉哥系列故事——完美隊形I
Time Limit: 3000/1000 MS (Java/Others) Memory Limit: 65535/32768 K (Java/Others)
Total Submission(s): 1367 Accepted Submission(s): 385
Problem Description
吉哥這幾天對隊形比較感興趣。
有一天,有n個人按順序站在他的面前,他們的身高分別是h[1], h[2] ... h[n],吉哥希望從中挑出一些人,讓這些人形成一個新的隊形,新的隊形若滿足以下三點要求,則稱之為完美隊形:
1、挑出的人保持他們在原隊形的相對順序不變;
2、左右對稱,假設有m個人形成新的隊形,則第1個人和第m個人身高相同,第2個人和第m-1個人身高相同,依此類推,當然,如果m是奇數,中間那個人可以任意;
3、從左到中間那個人,身高需保證遞增,如果用H表示新隊形的高度,則H[1] < H[2] < H[3] .... < H[mid]。
現在吉哥想知道:最多能選出多少人組成完美隊形?
Input
第一行輸入T,表示總共有T組數據(T <= 20);
每組數據先輸入原先隊形的人數n(1<=n <= 200),接下來一行輸入n個整數,表示按順序從左到右原先隊形位置站的人的身高(50 <= h <= 250,不排除特別矮小和高大的)。
Output
請輸出能組成完美隊形的最多人數,每組數據輸出占一行。
Sample Input
2
3
51 52 51
4
51 52 52 51
Sample Output
3
4
Source
2013騰訊編程馬拉松初賽第二場(3月22日)
Recommend
liuyiding
思路 :
把輸入序列倒置 求2者最長公共上升子序列
?#include<stdio.h> #include<string.h> int a[222],b[222],dp[222]; int get(int n,int m) { int i,j; memset(dp,0,sizeof(dp)); for(i=1;i<=n;i++) { int pos=0; for(j=1;j<=n-i+1;j++) { if(b[j]<a[i]&&dp[j]+1>dp[pos]) pos=j; if(b[j]==a[i]) { if(j!=(n-i+1))//不是自己和自己匹配了 { if(dp[j]<(dp[pos]+2)) dp[j]=dp[pos]+2; } else//自己和自己匹配了 { if(dp[j]<(dp[pos]+1)) dp[j]=dp[pos]+1; } //if(dp[j]<dp[pos]+1) // dp[j]=dp[pos]+1; } } } int ans=0; for(i=0;i<222;i++) if(dp[i]>ans) ans=dp[i]; return ans; } int main() { int cas,i,j,n; scanf("%d",&cas); while(cas--) { scanf("%d",&n); for(i=1;i<=n;i++) scanf("%d",&a[i]); j=1; for(i=n;i>=1;i--) b[i]=a[j++]; int ans=get(n,n); printf("%d\n",ans); } return 0; } #include<stdio.h> #include<string.h> int a[222],b[222],dp[222]; int get(int n,int m) { int i,j; memset(dp,0,sizeof(dp)); for(i=1;i<=n;i++) { int pos=0; for(j=1;j<=n-i+1;j++) { if(b[j]<a[i]&&dp[j]+1>dp[pos]) pos=j; if(b[j]==a[i]) { if(j!=(n-i+1))//不是自己和自己匹配了 { if(dp[j]<(dp[pos]+2)) dp[j]=dp[pos]+2; } else//自己和自己匹配了 { if(dp[j]<(dp[pos]+1)) dp[j]=dp[pos]+1; } //if(dp[j]<dp[pos]+1) // dp[j]=dp[pos]+1; } } } int ans=0; for(i=0;i<222;i++) if(dp[i]>ans) ans=dp[i]; return ans; } int main() { int cas,i,j,n; scanf("%d",&cas); while(cas--) { scanf("%d",&n); for(i=1;i<=n;i++) scanf("%d",&a[i]); j=1; for(i=n;i>=1;i--) b[i]=a[j++]; int ans=get(n,n); printf("%d\n",ans); } return 0; }
上面是從1開始輸入的 下面是蔥0開始輸入的 不知道為什麼總是錯
求大神指導下
?#include<stdio.h> #include<string.h> int a[222],b[222],dp[222]; int get(int n,int m) { int i,j; memset(dp,0,sizeof(dp)); for(i=0;i<n;i++) { int pos=0; for(j=0;j<=n-i-1;j++) { if(b[j]<a[i]&&dp[j]+1>dp[pos]) pos=j; if(b[j]==a[i]) { if(j!=(n-i-1))//不是自己和自己匹配了 { if(dp[j]<(dp[pos]+2)) dp[j]=dp[pos]+2; } else//自己和自己匹配了 { if(dp[j]<(dp[pos]+1)) dp[j]=dp[pos]+1; } //if(dp[j]<dp[pos]+1) // dp[j]=dp[pos]+1; } } } int ans=0; for(i=0;i<222;i++) if(dp[i]>ans) ans=dp[i]; return ans; } int main() { int cas,i,j,n; scanf("%d",&cas); while(cas--) { scanf("%d",&n); for(i=0;i<n;i++) scanf("%d",&a[i]); j=0; for(i=n-1;i>=0;i--) b[i]=a[j++]; int ans=get(n,n); printf("%d\n",ans); } return 0; } #include<stdio.h> #include<string.h> int a[222],b[222],dp[222]; int get(int n,int m) { int i,j; memset(dp,0,sizeof(dp)); for(i=0;i<n;i++) { int pos=0; for(j=0;j<=n-i-1;j++) { if(b[j]<a[i]&&dp[j]+1>dp[pos]) pos=j; if(b[j]==a[i]) { if(j!=(n-i-1))//不是自己和自己匹配了 { if(dp[j]<(dp[pos]+2)) dp[j]=dp[pos]+2; } else//自己和自己匹配了 { if(dp[j]<(dp[pos]+1)) dp[j]=dp[pos]+1; } //if(dp[j]<dp[pos]+1) // dp[j]=dp[pos]+1; } } } int ans=0; for(i=0;i<222;i++) if(dp[i]>ans) ans=dp[i]; return ans; } int main() { int cas,i,j,n; scanf("%d",&cas); while(cas--) { scanf("%d",&n); for(i=0;i<n;i++) scanf("%d",&a[i]); j=0; for(i=n-1;i>=0;i--) b[i]=a[j++]; int ans=get(n,n); printf("%d\n",ans); } return 0; }