算法题系列(一)

数串处理

一、题目描述

设有n个正整数,将他们连接成一排,组成一个最大的多位整数。
如:n=3时,3个整数13,312,343,连成的最大整数为34331213。
如:n=4时,4个整数7,13,4,246连接成的最大整数为7424613。

输入描述:

有多组测试样例,每组测试样例包含两行,第一行为一个整数N(N<=100),第二行包含N个数(每个数不超过1000,空格分开)。

输出描述:

每组数据输出一个表示最大的整数。

示例1

输入

2
12 123
4
7 13 4 246

输出

12312
7424613

二、解法思路

1、题目分析

题目要求:

n个正整数,将他们连接成一排,组成一个最大的多位整数。

要组成一个最大的多位整数,n个输入的正整数已经确定,所组成的多位整数的位数也已经确定,为所有正整数的位数之和。

那么只需要将最高位所在的数字最大的正整数放在最前面,最高位所在的数字第二大的数放在组合的第二位,以此类推。

上面的想法很简单,但是也可能出现两个正整数的最高位大小一样的情况,比如32和35。也有可能出现两个数前几位相同,但是位数不一样的情况。这些我们后面会考虑到。

2、算法设计

要解决这个问题,我的思路是创建一个方法Boolean compare(int a,int b),传入两个正整数a,b,返回整数a在组合时的优先权值是否高于整数b的bool值。

在设计好判断两个数在组合时的权值高低的方法之后,main方法中就可以直接通过任意的排序方法对输入的数组进行排序。只需要将传统排序算法的大小比较改成自己定义的权值判断方法即可。

比较权值的方法:

    /**
    * 比较两个整数在连成一排组和时的优先权
    * 方法:从两个数的最高位开始比较,如果当前位不相等,则结束。
    * 如果当前位相等且两个数不都是最后一位,则后移一位开始比较。
    * 已经达到最后一位的则仍然留在最后一位。
    */
    public static Boolean compare(int a,int b){
        int i = 0,j = 0;

        while (i < String.valueOf(a).length() || j < String.valueOf(b).length()){
            if(getNumberByIndex(a,i) > getNumberByIndex(b,j)){
                return true;
            }else if(getNumberByIndex(a,i) < getNumberByIndex(b,j)){
                return false;
            }else{
                i++;
                j++;
            }
        }
        return true;
    }

辅助方法(获取一个整数第 i 位的数字的方法):

    // 获取一个整数指定位的数字,高位->低位为0->max。
    // 如果所找的位数超过了数字的最大位,则返回最高位的数字。
    public static int getNumberByIndex(int n,int index){
        String number = String.valueOf(n);
        if (index < number.length()){
            return Integer.valueOf(number.charAt(index));
        }else{
            return Integer.valueOf(number.charAt(0));
        }
    }

三、完整代码


import java.util.Scanner;

/**
 * 题目描述
 * 设有n个正整数,将他们连接成一排,组成一个最大的多位整数。
 * 如:n=3时,3个整数13,312,343,连成的最大整数为34331213。
 * 如:n=4时,4个整数7,13,4,246连接成的最大整数为7424613。
 */


public class Test1 {
    public static void main(String[] args){
        Scanner input = new Scanner(System.in);
        do{
            int n = input.nextInt();
            int[] number = new int[n];
            for (int k = 0;k < n;k++){
                number[k] = input.nextInt();
            }

            //直接使用冒泡排序进行排序,将权值高的数放到前面
            for (int i = 0;i < n;i++){
                for (int j = n-1;j > i;j--){
                    if (compare(number[j],number[i])){
                        //交换number[i]和number[j]的位置
                        number[i] = number[i] + number[j];
                        number[j] = number[i] - number[j];
                        number[i] = number[i] - number[j];
                    }
                }
            }
            for(int each:number){
                System.out.print(each);
            }
            System.out.println();
        }while (input.hasNext());
    }

    /**
    * 比较两个整数在连成一排组和时的优先权
    * 方法:从两个数的最高位开始比较,如果当前位不相等,则结束。
    * 如果当前位相等且两个数不都是最后一位,则后移一位开始比较。已经达到最后一位的则仍然留在最后一位。
    */
    public static Boolean compare(int a,int b){
        int i = 0,j = 0;

        while (i < String.valueOf(a).length() || j < String.valueOf(b).length()){
            if(getNumberByIndex(a,i) > getNumberByIndex(b,j)){
                return true;
            }else if(getNumberByIndex(a,i) < getNumberByIndex(b,j)){
                return false;
            }else{
                i++;
                j++;
            }
        }
        return true;
    }

    // 获取一个整数指定位的数字,高位->低位为0->max。
    // 如果所找的位数超过了数字的最大位,则返回最高位的数字。
    public static int getNumberByIndex(int n,int index){
        String number = String.valueOf(n);
        if (index < number.length()){
            return Integer.valueOf(number.charAt(index));
        }else{
            return Integer.valueOf(number.charAt(0));
        }
    }
}

因为刚开始写博客,如果对您有帮助,希望能给我一个留言,这是对我最大的支持,谢谢。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值