Java题解—1015 德才论 (25 分)

原题

传送门

思路

1、首先分根据题意,分四类。
在大前提大于等于及格线下。第一类:都大于等于H。第二类:德大于等于H并且才小于H。第三类:德才小于H但德大于等于才。第四类:就是不满足上面三类但在及格线上的。
处理:我对每个类别,在条件判别后,用一个集合分别装入。

2、在分属的类里进行排序。
排序要求:总分降序。在总分相等时,德分降序。在总分和得分相等时,准考证号升序。
处理:因为总分和德分是,两个关键字的组合排序且排序方向一样,尝试拼接起来再比较拼接的数字大小,作逆向排序。
由于我把所有关键字都拼接起来了,准考证号需加一个判断,再对这组拼接数字作正向排序。

以下代码显得很多的是:字符串型拼接和具体关键字的截取。

还有利用了对象间的Comparator比较器排序。调用的是字符串默认排序方法。可以自己写更高效的比较排序。

代码

错误超时版

package pat;

import java.util.ArrayList;
import java.util.Comparator;
import java.util.Scanner;

public class Main {
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        int N=scanner.nextInt();
        int L=scanner.nextInt();
        int H=scanner.nextInt();

        //分成四个层次,用集合装
        ArrayList<String> group1 = new ArrayList<>();
        ArrayList<String> group2 = new ArrayList<>();
        ArrayList<String> group3 = new ArrayList<>();
        ArrayList<String> group4 = new ArrayList<>();
        int count=0;//计数

        for (int i=0;i<N;i++){
            int registrationNum=scanner.nextInt();//准考证号
            int moralGrade=scanner.nextInt();//德行分
            int brillianceGrade=scanner.nextInt();//才智分
            long total=moralGrade+brillianceGrade;//总分
            //先分层再排序
            if(moralGrade>=L && brillianceGrade>=L) {
                String examinee=total+"0"+moralGrade+""+registrationNum+"0"+brillianceGrade;
                //才德全尽
                if (moralGrade>=H&&brillianceGrade>=H){
                    count++;
                    //拼接加0,统一格式,分数三位数
                    if (moralGrade==100&&brillianceGrade==100)
                        group1.add(total+""+moralGrade+""+registrationNum+""+brillianceGrade);
                    else if(moralGrade!=100&&brillianceGrade==100)
                        group1.add(total+"0"+moralGrade+""+registrationNum+""+brillianceGrade);
                    else if(moralGrade==100&&brillianceGrade!=100)
                        group1.add(total+""+moralGrade+""+registrationNum+"0"+brillianceGrade);
                    else
                        group1.add(examinee);
                }
                //德胜才
                else if(moralGrade>H&&brillianceGrade<H){
                    group2.add(examinee);
                }
                //“才德兼亡”但尚有“德胜才”者
                else if (moralGrade<H && brillianceGrade<H && moralGrade>=brillianceGrade){
                    group3.add(examinee);
                }
                //其它
                else {
                    group4.add(examinee);
                }
            }
        }

        //输出
        System.out.println(count);
        sort(group1);
        sort(group2);
        sort(group3);
        sort(group4);
    }

      //对单个层次集合里的数据,按输出要求排序
    public static void sort(ArrayList<String> group){
        group.sort(new Comparator<String>() {
            @Override//189 090 10000013 099
            public int compare(String o1, String o2) {
                if (o1.substring(0,6).equals(o2.substring(0,6)))//前六位相等
                    return o1.compareTo(o2);
                else
                    return -o1.compareTo(o2);
            }
        });

        for (String s:group){//把序号、分数分离开分别打印
            String r=s.substring(6,14);
            int m=Integer.parseInt(s.substring(3,6));//把三位数转为两位数
            int b=Integer.parseInt(s.substring(14,17));

            System.out.println(r+" "+m+" "+b);
        }
    }

}

咳咳!我试着用对象来装记录,还是运行超时(抓狂)。不是拼接代码看起来稍微简单了一点。
参考

package pat;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Scanner;

/**
 * @Description
 */
public class Test {
    private static class Examinee implements Comparable<Examinee>{//考生类
        String id;
        int moralGrade;
        int brillianceGrade;
        int total;

        @Override
        public String toString() {
            return id+" "+moralGrade+" "+brillianceGrade;
        }
        //设定排序规则
        @Override
        public int compareTo(Examinee o) {
            if (this.total==o.total&&this.moralGrade==o.moralGrade)
                return id.compareTo(o.id);
            else if (this.total==o.total)
                return -Integer.compare(moralGrade,o.moralGrade);
            else
                return -Integer.compare(total,o.total);
        }
    }
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        int N=scanner.nextInt();
        int L=scanner.nextInt();
        int H=scanner.nextInt();

        ArrayList<Examinee> group1 = new ArrayList<>();
        ArrayList<Examinee> group2 = new ArrayList<>();
        ArrayList<Examinee> group3 = new ArrayList<>();
        ArrayList<Examinee> group4 = new ArrayList<>();
        int count=0;

        for (int i=0;i<N;i++){
            Examinee e = new Examinee();

            e.id=scanner.next();//准考证号
            e.moralGrade=scanner.nextInt();//德行分
            e.brillianceGrade=scanner.nextInt();//才智分
            e.total=e.moralGrade+e.brillianceGrade;//总分

            //先分类
            if(e.moralGrade>=L && e.brillianceGrade>=L) {
                count++;
                //才德全尽
                if (e.moralGrade>=H&&e.brillianceGrade>=H)
                    group1.add(e);
                //德胜才
                else if(e.moralGrade>=H)
                    group2.add(e);
                //“才德兼亡”但尚有“德胜才”者
                else if (e.moralGrade>e.brillianceGrade)
                    group3.add(e);
                //第四类
                else
                    group4.add(e);
            }
        }

        //输出
        System.out.println(count);
        //再排序(用集合工具实现自然排序)
        Collections.sort(group1);
        Collections.sort(group2);
        Collections.sort(group3);
        Collections.sort(group4);
        //集合四种迭代方法中的forEach方法
        group1.forEach(System.out::println);
        group2.forEach(System.out::println);
        group3.forEach(System.out::println);
        group4.forEach(System.out::println);

    }
}
posted @ 2021-10-18 15:30  Infinite_V胜  阅读(123)  评论(0)    收藏  举报