Java算法:给你一个整数num。你可以对它进行如下步骤恰好两次︰ 选择一个数字x (o <= x <= 9) . 选择另一个数字y (o <= y <= 9)。数字y可以等于。·将num中所有出现x

题目:

给你一个整数num。你可以对它进行如下步骤恰好两次︰

  • 选择一个数字x (o <= x <= 9) .
  • 选择另一个数字y (o <= y <= 9)。数字y可以等于x。
  • 将num中所有出现x的数位都用y替换。
  • ·得到的新的整数不能有前导0,得到的新整数也不能是0。
  • 令两次对num的操作得到的结果分别为a和b。

请你返回a和b的最大差值。

示例 1:

输入:num = 555
输出:888
解释:第一次选择 x = 5 且 y = 9 ,并把得到的新数字保存在 a 中。
第二次选择 x =5 且 y = 1 ,并把得到的新数字保存在 b 中。 现在,我们有 a = 999 和 b = 111 ,最大差值为 888

示例 2

输入:num = 9
输出:8
解释:第一次选择 x = 9 且 y = 9 ,并把得到的新数字保存在 a 中。 第二次选择 x = 9 且 y = 1 ,并把得到的新数字保存在 b 中。 现在,我们有 a = 9 和 b = 1 ,最大差值为 8

示例 3

输入:num = 123456
输出:820000

示例 4

输入:num = 10000
输出:80000

示例 5

输入:num = 9288
输出:8700

分析:


  • 先看第一个例子:

    num = 555
    输出 888
    第一次选择 x = 5 且 y = 9 ,并把得到的新数字保存在 a 中。
    第二次选择 x =5 且 y = 1 ,并把得到的新数字保存在 b 中。 现在,我们有 a = 999 和 b = 111 ,最大差值为 888

    第一次选择:x=5 y=9 此时y覆盖x 新数字a = 999 因为要最大差值,所以当b=111时侯,a-b的差值最大 因此,第二次选择y=1,x=5,y覆盖了x,此时b=111;

  • 在看第二个例子:

    输入:num = 123456
    输出:820000

    num=123456,想要得到最大差值,因为只改变一种数字,很容易想到:923456-103456=82000(得到的新的整数不能有前导0,得到的新整数也不能是0)
    因此,第一次选择:x=1,y=9,此时a=923456 第二次选择:因为不能有前导0,所以,此时选择x=2,y=0,此时b=103456
    因此最大差值为82000.

  • 因此,由上述的示例可得: 第一次选择x从最高位开始,如果最高位不为9,就覆盖9(y=9),否则就下一位,以此类推,不为9的最高位覆盖即可。


    第二次因为为最小的值,所以,依然从最高位开始看,与之相反,最小数字为0,因为题目给出条件:得到的新的整数不能有前导0,所以,为了最小,x是依然从最高位开始看,如果最高位>1,那么此时令y=1,覆盖x,如果最高位是1了,此时最高位,从下一位开始,依次往后,直到在某一位数字>1(不能为1,因为前导不能为0)了,那么x就为这一位的数字,因此使得y=0最小,覆盖x,得到的b为最小值,因此a-b的差值最大。

解题代码:

方法一:暴力解题:

 public int maxDiff(int num) {
        int x = 0;
        int y = 0;
        int q=0;
        
        String nums = String.valueOf(num);
        LinkedList<String> one = new LinkedList<>();
        LinkedList<String> two = new LinkedList<>();
        for (int i =0;i<nums.length();i++){
            one.add(String.valueOf(nums.charAt(i)));
            two.add(String.valueOf(nums.charAt(i)));
        }
        int []  a=new int[one.size()] ;
        int []  b=new int[one.size()] ;

        for (int i =0;i<nums.length();i++){
            a[i]= Integer.parseInt(one.get(i)) ;
            b[i]= Integer.parseInt(one.get(i)) ;
        }
        //数组转换完成
        for (int i = 0; i < a.length; i++) {
            if (a[i]==1&&i==0){
                q=a[i];
                x=1;
                y=9;
                x=y;
                a[i]=x;
                break;
            }else if (a[i]!=9){
                q=a[i];
                y=9;
                x=q;
                x=y;
                a[i]=x;
                break;
            }
        }
        for (int i = 0; i < a.length; i++){
            if (a[i]==q){
                y=9;
                x=q;
                x=y;
                a[i]=x;
            }
        }
        /最大max完成
        for (int i = 0; i < b.length; i++) {
            if (i==0&&b[0] > 1) {
                x = b[0];
                q=x;
                break;
            }else if (b[i] > 1&&i!=0) {
                x=b[i];
                q=x;
                break;
            }
        }
        if (b[0] > 1){
            for (int i = 0; i < b.length; i++){
                y=1;
                x=y;
                if (b[i]==q){
                    b[i]=x;
                }
            }
        }else {
            for (int i = 1; i < b.length; i++){
                if (b[i]==q&&b[i]==1){
                    y=1;
                    x=y;
                    b[i]=x;
                }
                else if (b[i]==q){
                    y=0;
                    x=y;
                    b[i]=x;

                }
            }
        }
        int max=0;
        int min = 0;
        for(int i=0;i<a.length;i++)
        {
            max=max*10+a[i];
            min = min*10+b[i];
        }
        int dve =max-min;
        
        return dve;
    }

方法二:贪心算法:(贪心算法详解可参考贪心算法)

 public int maxDiff(int num) {
        StringBuffer min_num = new StringBuffer(String.valueOf(num));
        StringBuffer max_num = new StringBuffer(String.valueOf(num));

        // 找到一个高位替换成 9
        int max_length = max_num.length();
        for (int i = 0; i < max_length; ++i) {
            char digit = max_num.charAt(i);
            if (digit != '9') {
                replace(max_num, digit, '9');
                break;
            }
        }

        // 将最高位替换成 1
        // 或者找到一个与最高位不相等的高位替换成 0
        int min_length = min_num.length();
        for (int i = 0; i < min_length; ++i) {
            char digit = min_num.charAt(i);
            if (i == 0) {
                if (digit != '1') {
                    replace(min_num, digit, '1');
                    break;
                }
            }
            else {
                if (digit != '0' && digit != min_num.charAt(0)) {
                    replace(min_num, digit, '0');
                    break;
                }
            }
        }

        return Integer.parseInt(max_num.toString()) - Integer.parseInt(min_num.toString());
    }

    public void replace(StringBuffer s, char x, char y) {
        int length = s.length();
        for (int i = 0; i < length; ++i) {
            if (s.charAt(i) == x) {
                s.setCharAt(i, y);
            }
        }
    }

方法三:枚举

   public int maxDiff(int num) {
        int min_num = num;
        int max_num = num;
        for (int x = 0; x < 10; ++x) {
            for (int y = 0; y < 10; ++y) {
                String res = change(num, x, y);
                // 判断是否有前导零
                if (res.charAt(0) != '0') {
                    int res_i = Integer.parseInt(res);
                    min_num = Math.min(min_num, res_i);
                    max_num = Math.max(max_num, res_i);
                }
            }
        }

        return max_num - min_num;
    }

    public String change(int num, int x, int y) {
        StringBuffer num_s = new StringBuffer(String.valueOf(num));
        int length = num_s.length();
        for (int i = 0; i < length; i++) {
            char digit = num_s.charAt(i);
            if (digit - '0' == x) {
                num_s.setCharAt(i, (char) ('0' + y));
            }
        }
        return num_s.toString();
    }
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

风儿吹吹吹

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值