华为OD真题--字符串摘要--带答案

更多2023面试系列在主页文章

 1. 华为OD机考题 + 答案

2023华为OD统一考试(A+B卷)题库清单-带答案(持续更新)

2023年华为OD真题机考题库大全-带答案(持续更新)

题目描述:

给定一个字符串的摘要算法,请输出给定字符串的摘要值

1、去除字符串中非字母的符号

2、如果出现连续字符 (不区分大小写) ,则输出: 该字符 (小) + 连续出现的次数

3、如果是非连续的字符(不区分大小写) ,则输出: 该字符(小写) 该字母之后字符串中出现的该字符的次数4、对按照以上方式表示后的字符串进行排序: 字母和紧随的数字作为一组进行排序,数字大的在前,数字相同的则按字母进行排序,字母小的在前。

输入描述:

行字符串,长度为[1,200]

输出描述:

摘要字符串

示例1

输入:

aabbcc

输出:

a2b2c2

示例2

输入:

bAaAcBb

输出:

a3b2b2c0

说明:

第一个b非连续字母,该字母之后字符串中还出现了2次 (最后的两个Bb) ,所以输出b2,a连续出现3次,输出a3,

c非连续,该字母之后字符串再没有出现过c,输出c0Bb连续2次,输出b2

对b2a3c0b2进行排序,最终输出a3b2b2c0

解题思路(非最优)

1. 使用正则表达式,将字母都获取出来

2. 使用双指针遍历

        2.1 使用标志位判断是否连续字母,还是相隔的字母

        2.2 连续的字母是累计当前次数+1,非连续字母是统计后面的字母数量

        2.3 连续字母中断后,将右指针的值赋值给左指针,跳过这连续字母的下标

        2.4 每次遍历后次数,右指针值重新赋值

        2.5 储存是小写字母数值,这里的储存使用对象

3. 排序

        3.1 先比较次数大小,相等在比较字母的顺序

public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        String value = sc.nextLine();
        StringBuffer sb = new StringBuffer();
        int index = 0;
        for (int i = 1; i <= value.length();i++){
            //1、去除字符串中非字母的符号
            Pattern pattern = Pattern.compile("[a-zA-Z]+");
            Matcher matcher = pattern.matcher((value.substring(index,i)));
            if (matcher.find()){
                sb.append(matcher.group());
            }
            index++;
        }
        List<Info> end = save(sb);
        sort(end);
    }


    public static List<Info> save(StringBuffer sb){
        //双指针
        int left = 0;
        int right = 1;
        int count = 0;
        Boolean flag = false;
        List<Info> infoList = new ArrayList<>();
        while (left != sb.length() && right != sb.length()) {
            //当前值
            String now = sb.substring(left, left + 1);
            //最后一个字符
            if (left + 1 == sb.length()) {
                Info info = new Info(0, now.toLowerCase(Locale.ROOT));
                infoList.add(info);
                break;
            }
            String after = sb.substring(right, right + 1);
            if (now.equalsIgnoreCase(after)) {
                count++;
                if (right - left <= 1) {
                    flag = true;//是否连续标志
                }
                if (right + 1 == sb.length()) {
                    if (flag) { //连续值+1
                        count++;
                    }
                    Info info = new Info(count, now.toLowerCase(Locale.ROOT));
                    infoList.add(info);
                    //移动右指针
                    right = left + 1;
                    left++; //移动左指针
                    count = 0;
                }
                right++;//连续值下标

            } else {
                // 2、如果出现连续字符 (不区分大小写) ,则输出: 该字符 (小) + 连续出现的次数
                if (flag) {//连续 中断时保存是数据
                    left = right;//跳过连续值
                    count++;
                    Info info = new Info(count, now.toLowerCase(Locale.ROOT));
                    infoList.add(info);
                    count = 0;
                    if (right + 1 == sb.length()) { //重新赋值右指针
                        right = left + 1;
                    }
                    // 3、如果是非连续的字符(不区分大小写) ,则输出: 该字符(小写) 该字母之后字符串中出现的该字符的次数
                } else if (!flag) { //非连续
                    if (right + 1 == sb.length()) {
                        Info info = new Info(count, now.toLowerCase(Locale.ROOT));
                        infoList.add(info);
                        count = 0;
                        right = left + 1;
                        left++;
                    }
                }
                right++;//跳过连续值
                if (right == sb.length()) {
                    right = left;
                }
                flag = false;
            }
        }
        return infoList;
    }

    /**
     * 4、对按照以上方式表示后的字符串进行排序: 字母和紧随的数字作为一组进行排序,数字大的在前,数字相同的则按字母进行排序,字母小的在前。
     * @param infoList
     */
    public static void sort(List<Info> infoList){
        Collections.sort(infoList,new SoutSummary());
        infoList.forEach(data -> System.out.print(data.getS() + data.getCount()));
    }

    static class SoutSummary implements Comparator<Info>{
        @Override
        public int compare(Info o1, Info o2) {
            //先比较次数的大小
            if (o1.getCount() > o2.getCount()){
                return -1;
            }else if (o1.getCount() < o2.getCount()){
                return 1;
                //如果次数相等
            }else {
                return o2.getS().compareTo(o2.getS());
            }
        }
    }



    static class Info{
        int count;
        String s;


        public Info(int count, String s){
            this.count = count;
            this.s = s;
        }

        public Info() {
        }

        public int getCount() {
            return count;
        }

        public void setCount(int count) {
            this.count = count;
        }

        public String getS() {
            return s;
        }

        public void setS(String s) {
            this.s = s;
        }
    }

猜你喜欢

转载自blog.csdn.net/weixin_42450130/article/details/132710236