《导弹拦截》题解

编程入门 行业动态 更新时间:2024-10-18 14:15:42

《导弹拦截》<a href=https://www.elefans.com/category/jswz/34/1769599.html style=题解"/>

《导弹拦截》题解

题目描述

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

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

输入格式

1行,若干个整数(个数≤100000)

输出格式

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

(1)这套系统最多能拦截多少导弹

我们只需找出所给数组的最长不上升子序列即可;

(2)如果要拦截所有导弹最少要配备多少套这种导弹拦截系统

        因为每个导弹拦截系统拦截的导弹每一发炮弹都不能高于前一发的高度, 因此我们只需统计出所给数组中的数字(该数字大于前面所有的数字)的数量即可, 既找出所给数组的最长上升子序列。

#include <iostream>
using namespace std;
const int N = 1e5 + 10;
int f[N], g[N], cnt, sum, n, a[N];
//a数组存储输入的数据, f存储最长不上升子序列, g数组存储最长上升子序列
//sum标记最长不上升子序列的末尾值的下标, cnt标记最长不上升子序列的末尾值的下标
int main()
{while (cin >> a[n]) n++;//存储输入数据f[0] = g[0] = a[0];//将第一个数字存进子序列中for (int i = 1; i < n; i++){if (a[i] <= f[sum])f[++sum] = a[i];//因为最长不上升子序列, 所以发现小于或等于子序列末尾值的都塞进子序列末尾else{int l = 0, r = sum;while (l < r){int m = l + r >> 1;if (f[m] < a[i])	r = m;else	l = m + 1;}//利用二分找第一个小于a[i]的值的下标f[l] = a[i];//更新找到的下标的值}//以下用同上种方式找出最长上升子序列if (a[i] > g[cnt])g[++cnt] = a[i];else{int l = 0, r = cnt;while (l < r){int m = l + r >> 1;if (g[m] >= a[i])	r = m;else	l = m + 1;}g[l] = a[i];}}cout << sum + 1 << endl << cnt + 1;//因为子序列下标从0开始,所以求出的值加一return 0;
}

更多推荐

《导弹拦截》题解

本文发布于:2024-03-10 05:48:24,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1727144.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:题解   导弹

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!