合唱队形(DP)
Posted darkfiremater
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了合唱队形(DP)相关的知识,希望对你有一定的参考价值。
【题目】
N位同学站成一排,音乐老师要请其中的(N-K)位同学出列,使得剩下的K位同学排成合唱队形。
合唱队形是指这样的一种队形:设K位同学从左到右依次编号为1,2…,K,
他们的身高分别为T1,T2,…,TK,则他们的身高满足 T1 < T2 ...< Ti > Ti+1 > … >TK(1<=i<=K)。
你的任务是,已知所有N位同学的身高,计算最少需要几位同学出列,可以使得剩下的同学排成合唱队形。
【输入格式】
第一行是一个整数N(2<=N<=100),表示同学的总数。
下来n个整数,用空格分隔,第i个整数Ti(130<=Ti<=230)是第i位同学的身高(厘米)。
【输出格式】
包括一行,这一行只包含一个整数,就是最少需要几位同学出列。
【样例输入】
8
186 186 150 200 160 130 197 220
【样例输出】
4
思路:
正着求一遍最长上升子序列和反着求一遍最长上升子序列即可。
1 #include<iostream> 2 #include<algorithm> 3 #include<cstring> 4 #include<iomanip> 5 #include<stdio.h> 6 #include<math.h> 7 #include<cstdlib> 8 #include<set> 9 #include<map> 10 #include<stack> 11 #include<queue> 12 #include<vector> 13 #include<set> 14 #define ll long long int 15 #define INF 0x7fffffff 16 #define mod 1000000007 17 #define me(a,b) memset(a,b,sizeof(a)) 18 #define PI acos(-1.0) 19 #define mian main 20 //size_t npos=-1; 21 //ios::sync_with_stdio(0),cin.tie(0); 22 using namespace std; 23 const int N=1e5+5; 24 25 int main() 26 { 27 int n,a[105],dp1[105],dp2[105]; 28 cin>>n; 29 for(int i=0;i<n;i++) 30 cin>>a[i]; 31 for(int i=0;i<n;i++){ 32 dp1[i]=1; 33 for(int j=0;j<i;j++){ 34 if(a[j]<a[i]) 35 dp1[i]=max(dp1[i],dp1[j]+1); 36 } 37 } 38 for(int i=n-1;i>=0;i--){ 39 dp2[i]=1; 40 for(int j=n-1;j>i;j--){ 41 if(a[j]<a[i]) 42 dp2[i]=max(dp2[i],dp2[j]+1); 43 } 44 } 45 int ans=0; 46 for(int i=0;i<n;i++){ 47 ans=max(ans,dp1[i]+dp2[i]-1); 48 } 49 cout<<n-ans<<endl; 50 }
以上是关于合唱队形(DP)的主要内容,如果未能解决你的问题,请参考以下文章