题目链接
题目描述
描述
每一个线段都有start和end两个数据项,表示这条线段在X轴上从start位置开始到end位置结束。
给定一批线段,求所有重合区域中最多重合了几个线段,首尾相接的线段不算重合。
例如:线段[1,2]和线段[2.3]不重合。
线段[1,3]和线段[2,3]重合
输入描述:
第一行一个数N,表示有N条线段
接下来N行每行2个数,表示线段起始和终止位置
输出描述:
输出一个数,表示同一个位置最多重合多少条线段
示例1
输入:
3
1 2
2 3
1 3
复制
输出:
2
思路
- 首先根据每个线段的左端点将线段进行排序
- 排序好的线段,依次处理,首先将第一个线段的右端点放入到小根堆中,然后将max设置为1,此时的最大值为自己这一条线段
- 然后从前往后依次处理每一个线段,如果遇到小根堆的堆顶元素比当前这个节点的左端点小或者相等,说明没有重合的元素,那么后边的线段也不可能会有重合的元素,因为我们是按照左端点进行排序的,所以如果遇到该情况一直弹出堆顶元素,然后将当前节点的右端点放入到堆中,并且求出一个max,当所有节点都遍历一遍后,也就找到了最大值。
时间复杂度
O(N * logN)
题解
import java.io.*;
import java.util.Arrays;
import java.util.Comparator;
import java.util.PriorityQueue;
class Node {
int l, r;
public Node(int l, int r) {
this.l = l;
this.r = r;
}
}
public class Main {
static int N = 10010;
static Node[] q = new Node[N];
public static void main(String[] args) throws Exception {
BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
int n = Integer.parseInt(reader.readLine());
for (int i = 0; i < n; i ++) {
String[] sps = reader.readLine().split(" ");
q[i] = new Node(Integer.parseInt(sps[0]), Integer.parseInt(sps[1]));
}
Arrays.sort(q, 0, n, Comparator.comparingInt(a -> a.l));
PriorityQueue<Integer> heap = new PriorityQueue<>();
int max = 1;
heap.add(q[0].r);
for (int i = 1; i < n; i ++) {
while (!heap.isEmpty() && heap.peek() <= q[i].l) {
heap.poll();
}
heap.add(q[i].r);
max = Math.max(heap.size(), max);
}
System.out.println(max);
}
}