LeetCode-670.最大交换(C++)

LeetCode-670.最大交换(C++)

题目原文

LeetCode-670.最大交换(原题链接)

题目描述
给定一个非负整数,你至多可以交换一次数字中的任意两位。返回你能得到的最大值。

示例1:

输入: 2736
输出: 7236
解释: 交换数字2和数字7。

示例2:

输入: 9973
输出: 9973
解释: 不需要交换。

注意:
给定数字的范围是 [ 0 , 108 ] [0, 108] [0,108]

解题思路

关键词:贪心

我们知道,将 n u m num num 转换成字符串 s s s 后, s [ i ] s[i] s[i] s [ j ] s[j] s[j] 交换( i i i 表示高位, j j j 表示低位), i i i 的值越小就越好(位数越高), s [ j ] s[j] s[j] 的值越大就越好。

所以从低位开始循环:对于每一位上的数,若其值大于低位上每个数的最大值,则这个数和低位上任何一位数交换都会使总体数值变小,故不交换,更新最大值,进行高一位的判断即可。

若其值小于低位上每个数最大值,则这个数和这个最大值进行交换可以一定程度上的提升总体数值,但此时并不一定是最优答案,因为 i i i 的值越小越好(位数越高),则若能在更高位找到满足相同条件的数(若其值小于低位上每个数最大值),更高位交换操作效果更优。所以记录此时答案,若更高位有解则更新答案。一直到循环结束。

若其值等于低位上每个数最大值,则不进行任何操作,原因:首先,二者交换整体数值没有任何变换(两数相等,不妨设均等于 x x x);其次,若是将当前位更新为最大值所在位,则后面出现解的时候,是高位 i i i 和这位交换( a [ i ] < x a[i] < x a[i]<x),交换结果是 . . . . . . x . . . . . . a [ i ] . . . . . . x ......x......a[i]......x ......x......a[i]......x,不更新最大值所在位,则交换后为 . . . . . . x . . . . . . x . . . . . . a [ i ] ......x......x......a[i] ......x......x......a[i],因为 a [ i ] < x a[i] < x a[i]<x,所以前者整体值明显小于后者(左边为高位,右边为低位)。

综上,可得完整代码,见下方。

完整代码

class Solution {
public:
    int maximumSwap(int num) {
        string s = to_string(num); //将数字转换为字符串
        int n = s.size(); //字符串长度
        
        int idx1 = -1, idx2 = -1, max_idx = n - 1; //用来记录关键下标
        for (int i = n - 1; i >= 0; i -- )
        {
            if (s[i] > s[max_idx]) max_idx = i;
            else if (s[i] < s[max_idx])
            {
                idx1 = i;
                idx2 = max_idx;
            }
        }
        
        if (idx1 != -1 && idx2 != -1) swap(s[idx1], s[idx2]);
        
        int res = stoi(s); //将字符串转换回数
        
        return res;
    }
};
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

星月满空江

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

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

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

打赏作者

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

抵扣说明:

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

余额充值