
华为OD机试 2024E卷题库疯狂收录中,刷题点这里
专栏导读
本专栏收录于《华为OD机试(JAVA)真题(E卷+D卷+A卷+B卷+C卷)》。
刷的越多,抽中的概率越大,私信哪吒,备注华为OD,加入华为OD刷题交流群,每一题都有详细的答题思路、详细的代码注释、3个测试用例、为什么这道题采用XX算法、XX算法的适用场景,发现新题目,随时更新,全天CSDN在线答疑。
一、题目描述
一个有N个选手参加的比赛,选手编号为1~N(3 <= N <= 100),有M(3 <= M <= 10)个评委对选手进行打分。
打分规则为每个评委对选手打分,最高为10分,最低为1分。
请计算得分最多的3位选手的编号。
如果得分相同,得分高分值最多的选手排名靠前。
(10分数量相同,则比较9分的数量,以此类推,用例中不会出现多个选手得分完全相同的情况。)
二、输入描述
第一行为半角逗号分割的两个正整数,第一个数字表示M(3 <= M <= 10)个评委,第二个数字表示N(3 <= N <= 100)个选手。
第2到M+1行为半角逗号分割的整数数组,表示评委对每个选手的打分,0号下标数字表示1号选手分数,1号下标数字表示2号选手分数,依次类推。
三、输出描述
选手前3名的编号。
注意:
若输入为异常,输出-1,如M、N、打分不在生范围内。
四、测试用例
测试用例1:
1、输入
4,5
 10,6,9,7,6
 9,10,6,7,5
 8,10,6,5,10
 9,10,8,4,9
2、输出
2,1,5
3、说明
第一行代表有4个评委,5个选手参加比赛 矩阵代表是4*5,每个数字是选手的编号,每一行代表一个评委对选手的打分排序, 2号选手得分36分排第1,1号选手36分排第2,5号选手30分(2号10分值有3个,1号10分值只有1个,所以2号排第一)
测试用例2:
1、输入
2,5
 7,3,5,4,2
 8,5,4,4,3
2、输出
-1
3、说明
只有2个评委,要求最少为3个评委
五、解题思路
- 遍历每个评委的打分,将每个选手的分数累加到 totalScore 中,并更新相应的 scoreCounts。
 - 总得分从高到低。
 - 若总得分相同,比较10分的数量,数量多的排名靠前;若10分数量相同,比较9分的数量,以此类推。
 - 取排序后的前3个选手的 id,用逗号分隔输出。
 - 如果输入不满足题目要求的格式或范围,直接输出 -1。
 
六、Java算法源码
public class OdTest01 {
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        try {
            // 读取第一行并解析M和N
            if (!scanner.hasNextLine()) {
                System.out.println("-1");
                return;
            }
            String firstLine = scanner.nextLine().trim();
            String[] mn = firstLine.split(",");
            if (mn.length != 2) { // 确保有两个数字
                System.out.println("-1");
                return;
            }
            int M = Integer.parseInt(mn[0].trim());
            int N = Integer.parseInt(mn[1].trim());
            // 验证M和N的范围
            if (M < 3 || M > 10 || N < 3 || N > 100) {
                System.out.println("-1");
                return;
            }
            // 初始化选手列表
            List<Contestant> contestants = new ArrayList<>();
            for (int i = 1; i <= N; i++) {
                contestants.add(new Contestant(i));
            }
            // 读取M行打分
            for (int i = 0; i < M; i++) {
                if (!scanner.hasNextLine()) { // 如果打分行不足M行
                    System.out.println("-1");
                    return;
                }
                String scoreLine = scanner.nextLine().trim();
                String[] scoresStr = scoreLine.split(",");
                if (scoresStr.length != N) { // 每行必须有N个分数
                    System.out.println("-1");
                    return;
                }
                for (int j = 0; j < N; j++) {
                    int score = Integer.parseInt(scoresStr[j].trim());
                    // 验证分数范围
                    if (score < 1 || score > 10) {
                        System.out.println("-1");
                        return;
                    }
                    contestants.get(j).addScore(score); // 为对应选手添加分数
                }
            }
            // 确保没有多余的打分行
            // 可以选择忽略,或进一步验证,视具体需求
            // 排序选手
            Collections.sort(contestants, new Comparator<Contestant>() {
                @Override
                public int compare(Contestant c1, Contestant c2) {
                    if (c2.totalScore != c1.totalScore) {
                        return c2.totalScore - c1.totalScore; // 总得分降序
                    }
                    // 如果总得分相同,比较分数分布
                    for (int i = 0; i < 10; i++) { // 从10分到1分
                        if (c2.scoreCounts[i] != c1.scoreCounts[i]) {
                            return c2.scoreCounts[i] - c1.scoreCounts[i]; // 分数数量降序
                        }
                    }
                    return 0; // 如果完全相同,保持原有顺序(题目保证不会有完全相同的情况)
                }
            });
            // 取前3名
            List<Integer> top3 = new ArrayList<>();
            for (int i = 0; i < 3; i++) {
                top3.add(contestants.get(i).id);
            }
            // 输出结果,用逗号分隔
            StringBuilder sb = new StringBuilder();
            for (int i = 0; i < top3.size(); i++) {
                sb.append(top3.get(i));
                if (i != top3.size() - 1) {
                    sb.append(",");
                }
            }
            System.out.println(sb.toString());
        } catch (Exception e) {
            // 捕获任何异常,输出-1
            System.out.println("-1");
        } finally {
            scanner.close(); // 关闭扫描器
        }
    }
}
// 定义选手类,包含编号、总得分和分数分布
class Contestant {
    int id; // 选手编号
    int totalScore; // 总得分
    int[] scoreCounts; // 分数分布,scoreCounts[0]表示10分的数量,scoreCounts[9]表示1分的数量
    public Contestant(int id) {
        this.id = id;
        this.totalScore = 0;
        this.scoreCounts = new int[10]; // 初始化分数分布数组
    }
    // 方法:添加一个分数
    public void addScore(int score) {
        this.totalScore += score; // 累加总得分
        if (score >=1 && score <=10) {
            this.scoreCounts[10 - score] += 1; // 更新对应分数的数量
        }
    }
}
 
七、效果展示
1、输入
4,2
 8,5
 5,6
 10,4
 8,9
2、输出
-1
3、说明
只有2个评委,要求最少为3个评委
🏆下一篇:华为OD机试 - 简易内存池 - 逻辑分析(Java 2024 E卷 200分)
🏆本文收录于,华为OD机试(JAVA)真题(E卷+D卷+A卷+B卷+C卷)
刷的越多,抽中的概率越大,私信哪吒,备注华为OD,加入华为OD刷题交流群,每一题都有详细的答题思路、详细的代码注释、3个测试用例、为什么这道题采用XX算法、XX算法的适用场景,发现新题目,随时更新,全天CSDN在线答疑。




















