POJ 1836 Alignment(LIS)

487人阅读 评论(0) 收藏 举报
分类:

Description
令到原队列的最少士兵出列后,使得新队列任意一个士兵都能看到左边或者右边的无穷远处
Input
第一行为士兵个数n(2<=n<=1000),第二行为每个士兵的身高h(0.5<=h<=2.5)
Output
输出最少出列士兵数
Sample Input
8
1.86 1.86 1.30621 2 1.4 1 1.97 2.2
Sample Output
4
Solution
题意即为求使数列程先递增后递减的形式需要去掉的数字个数,当然也可以直接递减或者只递减不递增,双向lis后,求出以某个士兵作为队伍最高点时其左边递增数列人数与其右边递减数列人数之和最大值即为出列最少士兵后的队伍,用队伍总人数减去求出的最大值即为出列士兵最少人数
Code

#include<cstdio>
#include<cstring>
#include<iostream>
using namespace std;
#define INF (1<<29)
#define maxn 1010
struct node
{
    int up,down;
}DP[maxn];//DP[i].up表示以第i个士兵为最高点时其左方递增序列人数,DP{i].down表示以第i个士兵为最高点时其右方递减序列人数 
int n;
float h[maxn];
float dp[maxn];
void LIS1() 
{
    for(int i=0;i<n;i++)
        dp[i]=10.0;
    for(int i=0;i<n;i++)
    {
        int t=lower_bound(dp+1,dp+n+1,h[i])-dp;
        DP[i].up=t;
        dp[t]=h[i];
    }
}
void LIS2()
{
    for(int i=0;i<n;i++)
        dp[i]=10.0;
    for(int i=n-1;i>=0;i--)
    {
        int t=lower_bound(dp+1,dp+n+1,h[i])-dp;
        DP[i].down=t;
        dp[t]=h[i];
    }
}
int main()
{
    while(scanf("%d",&n)!=EOF)
    {
        for(int i=0;i<n;i++)
            scanf("%f",&h[i]);
        memset(DP,0,sizeof(DP));//初始化 
        LIS1();//求正向递增数列 
        LIS2();//求反向递增数列 
        int max=0;
        for(int i=0;i<n-1;i++)//遍历所有点 
            for(int j=i+1;j<n;j++)
                if(max<DP[i].up+DP[j].down)//更新队伍最后人数最大值 
                    max=DP[i].up+DP[j].down;
        printf("%d\n",n-max);//队伍总人数减去队伍人数最大值即为出列士兵最小值 
    }
    return 0;
}
查看评论

OpenSource的末日?

OpenSource的末日? 蓝森林 http://www.lslnet.com 2000年3月30日 09:18   Olaf Beckman在Linux.com写了一篇文章,阐述为什么他认为 OP...
  • Virtual
  • Virtual
  • 2001-01-12 11:57:00
  • 832

最长不下降子序列(可以改成最长上升子序列)

#include #define maxn 101111 using namespace std; int a[maxn],b[maxn]; int Search(int num,int low,in...
  • lyc1635566ty
  • lyc1635566ty
  • 2016-07-29 17:26:08
  • 203

poj 1836 Alignment(最长上升子序列)

Alignment Time Limit: 1000MS   Memory Limit: 30000K Total Submissions: 17345   Accepted: 5697 ...
  • qq_27601815
  • qq_27601815
  • 2017-08-27 16:58:17
  • 66

poj 1836 Alignment( 最长上升(下降)子序列 )

http://poj.org/problem?id=1836 题意:给n个士兵的身高,要求每个士兵向左或向右能看向无穷远处(新队列呈三角形分布),最少要剔除几个士兵; 思路:对数列分别顺序,逆...
  • u013081425
  • u013081425
  • 2014-02-24 16:42:30
  • 835

最长上升子序列nlogn及n^2算法

这题目是经典的DP题目,也可叫作LIS(Longest Increasing Subsequence)最长上升子序列 或者 最长不下降子序列。很基础的题目,有两种算法,复杂度分别为O(n*logn)和...
  • patkritLee
  • patkritLee
  • 2016-02-21 12:34:09
  • 1041

最长上升子序列n*n和nlogn 算法

最长上升子序列是常见的DP问题.数组b[1]~b[n]中存放着n个数字, 从1~n都有,顺序不定。 第一种方法是n*n时间复杂度的算法,利用一个数组d[i](i从1到n)存放着以b[i]作为结尾的...
  • HE19930303
  • HE19930303
  • 2015-07-13 11:50:24
  • 307

poj 1836 Alignment (最长上升子序列 N*log(n))@

In the army, a platoon is composed by n soldiers. During the morning inspection, the soldiers are al...
  • yjf3151731373
  • yjf3151731373
  • 2017-03-06 15:27:45
  • 128

【最长上升子序列nlog(n)】

#include #include #include #include #include using namespace std; typedef long long LL; const int N...
  • m0_37953323
  • m0_37953323
  • 2017-09-21 22:09:41
  • 97

最长上升子序列问题的几种解法

最长上升子序列问题的几种解法 拿POJ 2533来说。 Sample Input 7 1 7 3 5 9 4 8 Sample Output(最长上升/非降子序列的长度) 4 从输入的序...
  • Wabrush
  • Wabrush
  • 2017-06-10 19:27:15
  • 604

最长上升子序列 详解

最长上升子序列 时间限制: 10 Sec   内存限制:128 MB 题目描述 给定一个序列,初始为空。现在我们将1到N的数字插入到序列中,每次将一个数字插入到一个特定的位置。我们想知道此时最长...
  • qfikh
  • qfikh
  • 2016-07-19 13:49:12
  • 913
    个人资料
    持之以恒
    等级:
    访问量: 59万+
    积分: 2万+
    排名: 284
    最新评论