POJ-1836-Alignment-双向LIS(最长上升子序列)(LIS+LSD)+dp
Write a program that, knowing the height of each soldier, determines the minimum number of soldiers which have to get out of line.
Input
There are some restrictions:
• 2 <= n <= 1000
• the height are floating numbers from the interval [0.5, 2.5]
Output
Sample Input
8
1.86 1.86 1.30621 2 1.4 1 1.97 2.2
Sample Output
4 题意:
给出一列士兵的身高(会有重复),要求求出剔除最少士兵使得每一个士兵往左或者右看可以看到该队列的尽头士兵,原有的位置不得改变。
注意:
- 不能直接排序去剔除除去最高士兵以外有重复的元素,因为题目要求原来的队列顺序不变。
- A soldier see an extremity if there isn't any soldiers with a higher or equal height than his height between him and that extremity.也就是说在最后得到的队列中,除了最高的那个士兵可以有重复身高之外,其他的士兵的身高不允许有重复。(这里需要纠正一下,最高的身高不允许有重复,不仅如此,所有的身高都不允许有重复,否则往左或者往右看都看不过去,会被等身高的人挡住)。即最多有一个极值。
思路:
相当于给一列数num[n],要求求删掉最少的个数,任取其中一个元素num[i],满足:1.num[0]~num[i]单调递增;2.num[i]~num[n-1]单调递减。即最多有一个极值。
求出一个LIS一个LDS(需要倒着扫),然后从队首到队尾枚举位置,最后ans=n−max(dp1[i]+dp2[i])。
原数据:1.86 1.86 1.30621 2 1.4 1 1.97 2.2
最长上升子序列:1.86
1.30621 2
1.30621 1.4 (1.4去替换掉了2的位置)
1 1.4 1.97 2.2 (1比1.30621更优,去替换掉了1.30621的位置,而后面的数据不需要更新)(最后凭借这个序列求出最长长度,这个的最长长度是和正确排序得出的长度是一样的)
(1.30621 1.4 1.97 2.2 )(而这个长度与上面那一组数据长度一样,这个是正确排序的长度)
最长长度:4
最长下降子序列:1.86 1.30621
2 1.30621
2 1.4
2 1.4 1
2 1.97 1
2.2 1.97 1
(1.86 1.30621 1;1.86 1.4 1;2 1.4 1)
最长长度:3
(需要注意的是:求出来的只是序列的最长上升或下降长度,但是里面的元素不一定是按照上升或者下降的顺序进行排好的,只是用一个更优的数据去替换掉了原有的数据的位置。) 针对该题时间复杂度问题:对于最长上升子序列问题有两种写法,正常写O(n2),怕超时可以用O(nlogn)的写法。
#include<iostream>
#include<stdio.h>
#include<string.h>
#include<algorithm>
#define inf 0x3f3f3f3f
using namespace std; float a[];
int dpup[];
int dpdown[]; int main()
{
std::ios::sync_with_stdio(false);
cin.tie();
cout.tie();
int n;
cin>>n;
memset(dpup,,sizeof(dpup));
memset(dpdown,,sizeof(dpdown));
for(int i=; i<n; i++)
cin>>a[i];
for(int i=; i<n; i++)
{
dpup[i]=;
for(int j=; j<i; j++)
{
if(a[j]<a[i])
{
dpup[i]=max(dpup[i],dpup[j]+);
}
}
}
//
// for(int i=0; i<n; i++)
// {
// dpdown[i]=1;
// for(int j=0; j<i; j++)
// {
// if(a[j]>a[i])
// {
// dpdown[i]=max(dpdown[i],dpdown[j]+1);
// }
// }
//
//这两个上升和下降序列单纯判断是没有问题的,但是在这一题中,这样判断会出现交叉的情况,所以不能这样子写 for(int i=n-; i>=; i--) //这里需要倒着扫
{
dpdown[i]=;
for(int j=n-; j>i; j--)
{
if(a[i]>a[j])
{
dpdown[i]=max(dpdown[j]+,dpdown[i]);
}
}
}
int ans=-inf;
for(int i=; i<n; i++)
{
for(int j=i+; j<n; j++)
{
// if(a[i]==a[j])
// ans=max(ans,dpup[i]+dpdown[j]-1);
// else
ans=max(ans,dpup[i]+dpdown[j]);
}
}
//这里的第二层循环从i+1开始,已经间接排除掉了顶峰会出现两个相等的情况
//不存在顶峰出现三个甚至更多的情况,因为之前求得时候一个单调递增,一个单调递减,要是重复只会重复一次
cout<<n-ans<<endl;
return ;
}
POJ-1836-Alignment-双向LIS(最长上升子序列)(LIS+LSD)+dp的更多相关文章
- POJ - 1631 Bridging signals(最长上升子序列---LIS)
题意:左右各n个端口,已知n组线路,要求切除最少的线路,使剩下的线路各不相交,按照左端口递增的顺序输入. 分析: 1.设左端口为l,右端口为r,因为左端口递增输入,l[i] < l[j](i & ...
- poj 2533 Longest Ordered Subsequence 最长递增子序列(LIS)
两种算法 1. O(n^2) #include<iostream> #include<cstdio> #include<cstring> using namesp ...
- POJ 3903 Stock Exchange (E - LIS 最长上升子序列)
POJ 3903 Stock Exchange (E - LIS 最长上升子序列) 题目链接:http://acm.hust.edu.cn/vjudge/contest/view.action ...
- POJ 1887 Testingthe CATCHER (LIS:最长下降子序列)
POJ 1887Testingthe CATCHER (LIS:最长下降子序列) http://poj.org/problem?id=3903 题意: 给你一个长度为n (n<=200000) ...
- POJ - 3903 Stock Exchange(LIS最长上升子序列问题)
E - LIS Time Limit:1000MS Memory Limit:65536KB 64bit IO Format:%I64d & %I64u Descripti ...
- POJ 1631 Bridging signals (LIS:最长上升子序列)
题意:给你一个长为n(n<=40000)的整数序列, 要你求出该序列的最长上升子序列LIS. 思路:要求(nlogn)解法 令g[i]==x表示当前遍历到的长度为i的所有最长上升子序列中的最小序 ...
- 动态规划(DP),最长递增子序列(LIS)
题目链接:http://poj.org/problem?id=2533 解题报告: 状态转移方程: dp[i]表示以a[i]为结尾的LIS长度 状态转移方程: dp[0]=1; dp[i]=max(d ...
- 2.16 最长递增子序列 LIS
[本文链接] http://www.cnblogs.com/hellogiser/p/dp-of-LIS.html [分析] 思路一:设序列为A,对序列进行排序后得到B,那么A的最长递增子序列LIS就 ...
- 算法设计 - LCS 最长公共子序列&&最长公共子串 &&LIS 最长递增子序列
出处 http://segmentfault.com/blog/exploring/ 本章讲解:1. LCS(最长公共子序列)O(n^2)的时间复杂度,O(n^2)的空间复杂度:2. 与之类似但不同的 ...
- poj 2533 Longest Ordered Subsequence 最长递增子序列
作者:jostree 转载请注明出处 http://www.cnblogs.com/jostree/p/4098562.html 题目链接:poj 2533 Longest Ordered Subse ...
随机推荐
- Python_day01——变量
变量 1.声明变量 name="钱成龙" 变量定义的规则: 变量名只能是 字母.数字或下划线的任意组合 变量名的第一个字符不能是数字 关键字不能声明为变量名 2.变量类型 整 ...
- NX二次开发-NXOpen::Drawings::DrawingSheet Class Reference
NX11+VS2013 #include <NXOpen/Section.hxx> #include <NXOpen/SectionCollection.hxx> #inclu ...
- jmeter登录之-动态参数
jmeter登录之-动态参数 1.抓包查看提交的登录参数 发现参数authenticity_token是动态的,每次都不一样,所以回放的时候就会失败 2.提取动态变化的参数-后置处理器(相当于LR的关 ...
- 用java打开一个本地文件
以下有三种方式打开 /** * 借助java.awt.Desktop打开 * @see 打开的目录或文件名中允许包含空格 */ private static void useAWTDesktop() ...
- mongodb 查询指定字段
@AutowiredMongoDatabase database; @Overridepublic List<Grid> getAdditionalGrid(String collecti ...
- git分布式版本控制系统权威指南学习笔记(四):git reset
文章目录 git reset目录树重写 git reset 重置 git reset目录树重写 git reset --soft 暂存区工作区不变 git reset --hard git reset ...
- java程序中线程cpu使用率计算
原文地址:https://www.imooc.com/article/27374 最近确实遇到题目上的刚需,也是花了一段时间来思考这个问题. cpu使用率如何计算 计算使用率在上学那会就经常算,不过往 ...
- Intel Pin基础
参考:http://software.intel.com/sites/landingpage/pintool/docs/62732/Pin/html/ http://blog.nruns.com/bl ...
- Codeforces 1191B Tokitsukaze and Mahjong
题目链接:http://codeforces.com/problemset/problem/1191/B 题意:类似于麻将,三个一样花色一样数字的,或者三个同花顺就赢了,新抽的能当任何类型,问至少几个 ...
- Java 自动检测文本文件编码
private String guessCharset(InputStream is) throws IOException { return new TikaEncodingDetector().g ...