思路:
用一个list存储学生的安全指数y和是否挂科r,并用安全指数排序
预测正确的个数 = <y的0个数 + >=y的1个数
数组c0存储取每个安全指数y时,<y的0个数
注意:c0[0] = 0
数组c1存储取每个安全指数y时,>=y的1个数
注意:c1[m-1] = 1 (当list.get(m-1).r==1时)
c1[m-1] = 0 (否则)
在计算c0和c1其他元素时用到一维前缀和
map集合存储安全指数y和其对应预测正确的个数(用map是为了去重复的安全指数y)
遍历map取结果即可
代码:
import java.util.*;
public class Main implements Comparator<Score> {
public static void main(String[] args) {
Scanner scan = new Scanner(System.in);
int m = scan.nextInt(); // m位同学
List<Score> list = new ArrayList<>(); // 存储m位同学的安全指数y和是否挂科r
for (int i = 0; i < m; i++) {
int yi = scan.nextInt();
int ri = scan.nextInt();
Score sc = new Score(yi, ri);
list.add(sc);
}
// 对list按照安全指数y排序
Collections.sort(list, new Main());
int[] c0 = new int[m]; // <y里0的个数
int[] c1 = new int[m]; // >=y里1的个数c1
Map<Integer, Integer> c = new HashMap<>();; //每个安全指数y对应的预测正确的个数 c = c0+c1;记得去重复的y和对应的c
c0[0] = 0;
for (int i=1;i<m;i++){
if(list.get(i-1).r==0) {
c0[i] = c0[i - 1] + 1; // 一维前缀和
}else {
c0[i] = c0[i - 1];
}
}
if (list.get(m - 1).r == 1) {
c1[m - 1] = 1;
} else {
c1[m - 1] = 0;
}
for (int i=m-2;i>=0;i--){
if (list.get(i).r == 1){
c1[i] = c1[i+1] +1; // 一维前缀和
}else{
c1[i] =c1[i+1];
}
}
for(int i=0;i<m;i++){
if (!c.containsKey(list.get(i).y)){
c.put(list.get(i).y, c0[i]+c1[i]);
}
}
int maxc = -1;
int maxy = -1;
for(Integer y:c.keySet()){
if (c.get(y) > maxc){
maxc = c.get(y);
maxy = y;
}
if (c.get(y) == maxc){
maxc = c.get(y);
maxy = Math.max(maxy, y);
}
}
System.out.println(maxy);
}
public int compare(Score s1, Score s2) {
return s1.y - s2.y;
}
}
class Score {
int y;
int r;
public Score(int y, int r) {
this.y = y;
this.r = r;
}
}