AcWing 1014. 登山

原题链接

考察:线性dp

题目本质:求最长上升子序列+下降子序列

易错:

      这种题一般都要求下降子序列

      j>=i,避免 100 100 100这种数据

也可以用朴素法求,但是要预处理长度数组.

 1 #include <iostream>
 2 #include <cstring>
 3 #include <algorithm>
 4 #include <cstdio>
 5 using namespace std;
 6 const int N = 1010;
 7 int h[N],f[N],len,g[N];
 8 int main()
 9 {
10 //    freopen("in.txt","r",stdin); 
11     int n,ans = 0;
12     scanf("%d",&n);
13     for(int i=1;i<=n;i++) scanf("%d",&h[i]);
14     for(int i=1;i<=n;i++)
15     {
16         int low = 0,high = len,len2 = 0;
17         while(low<high)
18         {
19             int mid = low+high+1>>1;
20             if(f[mid]<h[i]) low = mid;
21             else high = mid-1;
22         }
23         f[low+1] = h[i];
24         len = max(len,high+1);
25         memset(g,0,sizeof g);
26         for(int j=n;j>=i;j--)
27         {
28             int l = 0,r = len2;
29             while(l<r)
30             {
31                 int mid = l+r+1>>1;
32                 if(g[mid]<h[j]) l = mid;
33                 else r = mid-1;
34             }
35             g[l+1] = h[j];
36             len2 = max(r+1,len2);
37         }
38         if(g[len2]==h[i]) ans = max(len+len2-1,ans);
39         else ans = max(len+len2,ans);
40     }
41     printf("%d\n",ans);
42     return 0;
43 }

 

posted @ 2021-02-06 00:31  acmloser  阅读(62)  评论(0编辑  收藏  举报