题目位置

https://www.luogu.org/problemnew/show/P1020

题目描述

某国为了防御敌国的导弹袭击,发展出一种导弹拦截系统。但是这种导弹拦截系统有一个缺陷:虽然它的第一发炮弹能够到达任意的高度,但是以后每一发炮弹都不能高于前一发的高度。某天,雷达捕捉到敌国的导弹来袭。由于该系统还在试用阶段,所以只有一套系统,因此有可能不能拦截所有的导弹。

输入导弹依次飞来的高度(雷达给出的高度数据是不大于50000的正整数),计算这套系统最多能拦截多少导弹,如果要拦截所有导弹最少要配备多少套这种导弹拦截系统。

输入输出格式

输入格式:

一行,若干个整数(个数少于100000)

输出格式:

2行,每行一个整数,第一个数字表示这套系统最多能拦截多少导弹,第二个数字表示如果要拦截所有导弹最少要配备多少套这种导弹拦截系统。

输入输出样例

输入样例#1:

389 207 155 300 299 170 158 65

输出样例#1:

6

2

对于此题有贪心与dp两种思路

dp思路

对于dp思路,很容易看出,第一问就是最长不上升自序列。

最长上升子序列我们都可以瞬间写完,那最长不上升子序列怎么办??

1、一开始我的思路是反着存一个数组,用反着的数组找最长上升子学列就好了,然而实践证明,似乎不可行........(可能是我太菜,细节出了问题),但是你如果有兴趣可以试一下,再来打我的脸...。

2、下面就说可行的思路,将求上升子学列中的一个f数组增为两个,f用来存正数,另一个ff存f的相反数,这样判断时用f进行判断,找数时用ff查找(如果一脸懵逼也没关系,后面代码一目了然)。最后输出f长度就ok了。

第二问呢就是求一个最长上升子序列

证明也很简单,只要你的炮弹高度上升了,肯定就要建一个新炮台,这时最长的上升子学列才能保证每次增长都有炮台被建,所有跑一遍模板就好了。只要想明白了这个,这就是一道大水题了,哈哈哈哈!

dp代码

 #include<cstdio>
#include<iostream>
#include<cstring>
#include<algorithm>
using namespace std;
int a[],f[],ff[],n;
int main()
{
while(cin>>a[++n]);//不多bb
n--;
int len=;
f[len]=a[];ff[]=-a[];//f数组用来存正的数,ff存其相反数
for(int i=;i<=n;++i)//最长不上升子学列
{
if(a[i]<=f[len])//判断时用f找更小的
{
f[++len]=a[i];
ff[len]=-a[i];//取反存入ff
}
else
{
int v=upper_bound(ff+,ff+len+,-a[i])-ff;//用ff寻找最大的比a[i]小的数
f[v]=a[i];
ff[v]=-a[i];
}
}
printf("%d\n",len);
memset(f,,sizeof(f));
memset(ff,,sizeof(ff));
len=;
f[]=a[];
for(int i=;i<=n;++i)//一遍最长上升子学列
{
if(a[i]>f[len]) f[++len]=a[i];
else
{
int v=lower_bound(f+,f+len+,a[i])-f;
f[v]=a[i];
}
}
printf("%d",len);//拜拜
return ;
}

贪心思路

对于第一问,我没有想出其他思路(尴尬qwq......)

对于第二问,我就有要说的

其实我也不知道我的思路算不算贪心了....就姑且起这个名字吧(总不能还叫dp)

第二问要求找出最少的炮台数,那我们就从第一个炮弹开始,如果这个炮弹不能被击落,就安装一架炮台,然后把后面的炮弹按照规则能打掉的标记为能击落(注意题目中说炮台所能击打的高度递减)。

然后知道所有炮弹都被标记为能击落,结束。

下面给予证明

9  1  2  5  3  2  9  1  

  对于以上数据,按照我们的思路先在9处安一架炮台,然后将1标记为可以被击落,结束这次查找。

  或许有人会问,用这座炮台打击5 3 2 1不是更划算吗??

  似乎是这样,但是我们设想,用9的这座炮台打掉了1,那么在2是再安一座,5时再按一座,下一个9时再安一座,总共4座。

  如果按照打掉5 3 2 1的方法,那么9时安一座,1时安一座,2时安一座,下一个9也要安一座,共4座。。。。。

  巧合????

  其实不是,因为如果你考虑打掉最多的,那么你躲开不打得那些总是要被击落的,只好他们自己再安一座,这时你似乎省掉了炮台,但实际并不。

  这个要考自己去感悟,其实与dp思路有异曲同工之妙。

贪心代码

 #include<cstdio>
#include<iostream>
#include<algorithm>
using namespace std;
int a[],n,f[],ff[],vis[],ans,js,zz;
int main()
{
while(cin>>a[++n]);
n--;
int len=;
f[++len]=a[];ff[len]=-a[];//从这到26行与dp思路相同,不多bb
for(int i=;i<=n;++i)
{
if(a[i]<=f[len])
{
f[++len]=a[i];
ff[len]=-a[i];
}
else
{
int v=upper_bound(ff+,ff+len+,-a[i])-ff;
f[v]=a[i];
ff[v]=-a[i];
}
}
printf("%d\n",len);
for(int i=;i<=n;++i)//从第一个开始扫
{
if(!vis[i])//用vis来记录是否被打掉
{
zz=a[i];ans++;//ans记录炮台数
for(int j=i;j<=n;++j)//将后面的vis更新
{
if(a[j]<=zz&&!vis[j])
{
zz=a[j];//zz用来存当前能击打的最高高度
vis[j]=; js++;//js用来记录被击落的炮弹数,便于结束循环
} }
}
if(js==n)//炮弹全部击落,输入答案,结束程序
{
printf("%d",ans);
return ;
}
}
return ;
}

如果有我瞎bb错的地方,欢迎指教订正!!!

[luogu1020][导弹拦截]的更多相关文章

  1. HDU-1257 导弹拦截系统 http://acm.hdu.edu.cn/showproblem.php?pid=1257

    Problem Description 某国为了防御敌国的导弹袭击,发展出一种导弹拦截系统.但是这种导弹拦截系统有一个缺陷:虽然它的第一发炮弹能够到达任意的高度,但是以后每一发炮弹都不能超过前一发的高 ...

  2. AC日记——导弹拦截 洛谷 P1020 (dp+模拟)

    题目描述 某国为了防御敌国的导弹袭击,发展出一种导弹拦截系统.但是这种导弹拦截系统有一个缺陷:虽然它的第一发炮弹能够到达任意的高度,但是以后每一发炮弹都不能高于前一发的高度.某天,雷达捕捉到敌国的导弹 ...

  3. 【codevs1044】导弹拦截问题与Dilworth定理

    题目描述 Description 某国为了防御敌国的导弹袭击,发展出一种导弹拦截系统.但是这种导弹拦截系统有一个缺陷:虽然它的第一发炮弹能够到达任意的高度,但是以后每一发炮弹都不能高于前一发的高度.某 ...

  4. TYVJ P1020 导弹拦截 Label:水

    题目描述 某国为了防御敌国的导弹袭击,发展出一种导弹拦截系统.但是这种导弹拦截系统有一个缺陷:虽然它的第一发炮弹能够到达任意的高度,但是以后每一发炮弹都不能高于前一发的高度.某天,雷达捕捉到敌国的导弹 ...

  5. bzoj2044: 三维导弹拦截

    Description 一场战争正在A国与B国之间如火如荼的展开. B国凭借其强大的经济实力开发出了无数的远程攻击导弹,B国的领导人希望,通过这些导弹直接毁灭A国的指挥部,从而取得战斗的胜利!当然,A ...

  6. nyoj 79 导弹拦截

    点击打开链接 拦截导弹 时间限制:3000 ms  |  内存限制:65535 KB 难度:3 描述 某国为了防御敌国的导弹袭击,发展中一种导弹拦截系统.但是这种导弹拦截系统有一个缺陷:虽然它的第一发 ...

  7. UESTC_导弹拦截 2015 UESTC Training for Dynamic Programming<Problem N>

    N - 导弹拦截 Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) Submit  ...

  8. [vijosP1303]导弹拦截(最长上升子序列转LCS)

    描述 某国为了防御敌国的导弹袭击,研发出一种导弹拦截系统.但是这种导弹拦截系统有一个缺陷:虽然它的第一发炮弹能够到达任意的高度,但是以后每一发炮弹都不能高于前一发的高度.某天,雷达捕捉到敌国的导弹来袭 ...

  9. noip提高组1999 导弹拦截

    导弹拦截 背景 实中编程者联盟为了培养技术精湛的后备人才,必须从基础题开始训练. 描述 某国为了防御敌国的导弹袭击,研发出一种导弹拦截系统.但是这种导弹拦截系统有一个缺陷:虽然它的第一发炮弹能够到达任 ...

随机推荐

  1. js获取数组中相同元素数量

    <script> var array = new Array(1,2,5,1,4,4,2,3,5,1,1,5,5,5,6,7,3,9,9,10); var arr = new Array( ...

  2. 【apache2】AH00543: httpd: bad user name apache

    当启动 apache 时,出现一下异常:AH00543: httpd: bad user name daemon 解决方法:            #groupadd daemon          ...

  3. @Autowired 与@Resource的区别(详细)

    参考:@Autowired 与@Resource的区别(详细) spring不但支持自己定义的@Autowired注解,还支持几个由JSR-250规范定义的注解,它们分别是@Resource.@Pos ...

  4. FormDestroy 和 FormClose 有什么区别和联系?

    1.窗口的所有资源真正释放时调用 FormDestroy.当你关闭窗口时,VCL会调用FormClose,如果你在FormClose里写Action = caFree,那么VCL会继续调用FormDe ...

  5. 解析xml文件 selectSingleNode取不到节点

    今天在做批量生成XML的时候,碰到一个情况 解析xml文件 selectSingleNode一直返回NULL. XML的格式开头有一句这个<CE401Message xmlns="ht ...

  6. 学习 Spring (十六) AOP API

    Spring入门篇 学习笔记 Spring AOP API 是 Spring 1.2 历史用法,现在仍然支持 这是 Spring AOP 基础,现在的用法也是基于历史的,只是更简便了 Pointcut ...

  7. 1.rabbitmq高可用方案

    采用标准集群模式  HAPROXY + rabbitmq 2个 ram  和  一个 disk 节点 主机规划: 192.168.157.128 haproxy keepalive 主 ram节点 1 ...

  8. Rest模式get,put,post,delete含义与区别

    POST   /uri     创建   DELETE /uri/xxx 删除    PUT    /uri/xxx 更新或创建   GET    /uri/xxx 查看   GET操作是安全的.所谓 ...

  9. Android热修复原理

    参考:https://www.cnblogs.com/popfisher/p/8543973.html 一. AndFix AndFix的原理就是方法的替换,把有bug的方法替换成补丁文件中的方法.  ...

  10. Go语言流程控制

    1.条件语句 几个注意点和C#不一样的. { } else { } ① 条件语句不需要使用括号将条件包含起来 a<5 ,C#必须有() ②无论语句体内有几条语句,花括号{}都是必须存在的:C#如 ...