POJ 1836 Alignment

Posted 谦谦君子,陌上其华

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了POJ 1836 Alignment相关的知识,希望对你有一定的参考价值。

http://poj.org/problem?id=1836

题意:给出一排士兵的身高,求出至少需要移除多少个士兵可以使得剩下的士兵往左看或者是往右看可以看到无穷远处。

思路:士兵的分布最终要呈三角形分布,我们从左边和右边分别求一个最长递增子序列,然后最后只需要一一枚举就可以了。

 1 #include<iostream> 
 2 #include<algorithm>
 3 using namespace std;
 4 
 5 const int maxn = 1000 + 5;
 6 
 7 int dp_L[maxn], dp_R[maxn]; // 分别代表从左、右边开始的LIS长度  
 8 double a[maxn]; // 身高  
 9 
10 int main()
11 {
12     //freopen("D:\\txt.txt", "r", stdin);
13     int n;
14     while (cin>>n && n)
15     {
16         for (int i = 0; i < n; i++)
17             cin >> a[i];
18 
19         dp_L[0] = dp_R[n - 1] = 1;
20 
21         for (int i = 1; i<n; i++)
22         { // 从左边求LIS长度  
23             dp_L[i] = 1;   //最坏情况是左边的都比他高,那么此时LIS就为1
24             for (int j = 0; j<i; j++)
25             if (a[j] < a[i])
26                 dp_L[i] = max(dp_L[i], dp_L[j] + 1);
27         }
28 
29         for (int i = n - 2; i >= 0; i--)
30         { 
31             dp_R[i] = 1;
32             for (int j = n - 1; j>i; j--)
33             if (a[j] < a[i])
34                 dp_R[i] = max(dp_R[i], dp_R[j] + 1);
35         }
36         int ans = 0;
37         //依次枚举情况
38         for (int i = 0; i < n - 1; i++)
39         for (int j = i + 1; j < n; j++)
40             ans = max(ans, dp_L[i] + dp_R[j]);
41         cout << n - ans << endl;
42     }
43     return 0;
44 }

 

以上是关于POJ 1836 Alignment的主要内容,如果未能解决你的问题,请参考以下文章

[poj 1836] Alignment dp

POJ 1836 Alignment

POJ-1836 Alignment---LIS

POJ 1836-Alignment(DP/LIS变形)

POJ 1836 Alignment(DP max(最长上升子序列 + 最长下降子序列))

POJ 1836 Alignment 最长递增子序列(LIS)的变形