本文主要是介绍蓝桥杯-导弹拦截-贪心,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
蓝桥杯-导弹拦截-贪心-dp-java
输入导弹依次飞来的高度(雷达给出的高度数据是不大于30000的正整数),计算这套系统最多能拦截多少导弹,如果要拦截所有导弹最少要配备多少套这种导弹拦截系统。
2
解题思路: 这题的本质就是最长下降子序列
下降上升都一样 这个不是重点
求解此类问题 有两种方式
1.dp n*n 时间复杂度
1–n 第i个位置的最长子序列 = max(1— i-1)+1
2.二分查找 n*logn时间复杂度
建立一个空数组 每次放在数组的数都和最后一个数进行比较 符合要求就放入数组的末尾
不符合要求 就进入此时的数组进行二分查找 那么找啥呢? 看要求 比如本题求的是最长下降子序列 那么就找
比他大的第一个数的位置+1 的位置 然后将此位置的值 换成他 就可以了 如果不明白 可以自己找点数 模拟一遍就很好懂
注意:我写此题的时候用的是第二种 但这是不对的 这种方法只能求序列第一遍的最大子序列的长度 注意是长度
所以这个不能这么用
下面是ac代码 有一部分注释
import java.util.ArrayList;
import java.util.Scanner;
public class Main{
public static void main(String[] args) {
// TODO Auto-generated method stub
Scanner scanner = new Scanner(System.in);
while (scanner.hasNext()) {
String [] str = scanner.nextLine().split(” “);
int [] arr = new int [str.length];
for (int i = 0; i < arr.length; i++) {
arr[i] = Integer.parseInt(str[i]);
}
boolean [] flag = new boolean [arr.length];//记录已经被拦截的导弹
int max = 0;//最大下降子序列的长度
int num = 0;//需要几套导弹系统
int sum = 0;//记录导弹拦截总数 用于跳出while循环
while (sum != arr.length) { //当所有导弹被拦截 就结束循环
ArrayList [] lists = new ArrayList [arr.length];
for (int i = 0; i < lists.length; i++) {
lists[i] = new ArrayList<Integer>();
}//记录每个子序列
int index = 0; //最大子序列的下标
int childMax = 0; //最大子序列的长度
int k = 0;
for (int i = 0; i < arr.length; i++) {
if (flag[i]) {
continue;
}
if (k == 0) {
k ++;
lists[i].add(i);
childMax = 1;
index = i;
}else {
int maxLength = -1;
int maxIndex = -1;
for (int j = i-1; j >= 0; j–) {
if (flag[j]) {
continue;
}
if (arr[i] < arr[j]) {
maxLength = maxLength > lists[j].size() ? maxLength : lists[j].size();
maxIndex = maxLength > lists[j].size() ? maxIndex : j;
}
}
if (maxIndex == -1) {
lists[i].add(i);
}else {
for (int j = 0; j < lists[maxIndex].size(); j++) {
lists[i].add(lists[maxIndex].get(j));
}
lists[i].add(i);
}
childMax = childMax > lists[i].size() ? childMax : lists[i].size();
index = childMax > lists[i].size() ? index : i;
}
}
for (int i = 0; i < lists[index].size(); i++) {
flag[(int) lists[index].get(i)] = true;
}
max = max > childMax ? max : childMax;
num ++;
sum += childMax;
}
System.out.println(max + “\n” + num);
}
}
}
相关文章
分拆素数和 (hdu 2098)
动态规划---子串查询 (前缀和的应用)
确定比赛次序(topesort)
还是畅通工程 (并查集+权值)
畅通工程再续 (hdu1875)
Let the Balloon Rise (map的应用)
前m大的数 (普通方法+哈希算法)
Number Sequence (KMP)
剪花布条 (KMP)
这篇关于蓝桥杯-导弹拦截-贪心的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!