zoukankan      html  css  js  c++  java
  • LeetCode 564. Find the Closest Palindrome (构造)

    题意:

    给一个数字n 求离n最近(且不等)的回文串 存在多个答案返回最小的

    首先很容易想到

    将数字分为两段,如 12345 -> 123/45,然后将后半段根据前面的进行镜像重置 123/45 -> 12321

    那,如果数字刚好是回文串,就把前半段-1就好了

    但是存在以下例外,就是当前半段 +1 或 -1 就会造成进位

    10999

    10901-10999 = -98

    11011 - 10999 = -12

    可以发现是因为9存在的进位,同样0也可能,所以对前半段进行 +1 和 -1 两种处理,然后选择差比较小的那个。

    代码写的比较乱= =

    class Solution {
    public:
        string nearestPalindromic(string n) {
            typedef long long ll;
            if (n == "10" || n == "11") return "9";
            
            int l = n.size();
            int half = (l + 1) / 2;
            string left = n.substr(0, half);
            string right = n.substr(half);
            
            // 情况1: 直接镜像翻转
            string ans1 = (l & 1) ? left + rev_str(left).substr(1) : left + rev_str(left);
            // 如果和原数字相同则不可用
            ll diff1 = ans1 == n ? stoll(n) : abs(stoll(ans1) - stoll(n));
            
            // 情况2: -1
            string left_sub_1 = to_string(stoll(left) - 1);
            string rleft_sub_1 = rev_str(left_sub_1);
            string ans2;
            if (left_sub_1.size() < half) {
                ans2 = (l & 1)
                    ? left_sub_1 + rleft_sub_1
                    : left_sub_1 + "9" + rleft_sub_1;
            }
            else {
                ans2 = (l & 1)
                    ? left_sub_1 + rleft_sub_1.substr(1)
                    : left_sub_1 + rleft_sub_1;
            }
            ll diff2 = abs(stoll(ans2) - stoll(n));
            
            // 情况3: +1
            string left_add_1 = to_string(stoll(left) + 1);
            string rleft_add_1 = rev_str(left_add_1);
            string ans3;
            if (left_add_1.size() > half) {
                ans3 = (l & 1) 
                    ? left_add_1 + rleft_add_1.substr(2) 
                    : left_add_1 + rleft_add_1.substr(1);
            }
            else {
                ans3 = (l & 1)
                    ? left_add_1 + rleft_add_1.substr(1)
                    : left_add_1 + rleft_add_1;
            }
            ll diff3 = abs(stoll(ans3) - stoll(n));
            
            if (diff2 <= diff1 && diff2 <= diff3) return ans2;
            if (diff1 <= diff2 && diff1 <= diff3) return ans1;
            return ans3;
        }
        
        string rev_str(string a) {
            string b(a);
            reverse(b.begin(), b.end());
            return b;
        }
    };
  • 相关阅读:
    C语言inline函数(转)
    C++ 输入ctrl+z 不能再使用cin的问题
    VMware无法识别USB设备
    python manage.py 命令
    求二叉树的最小深度
    Vim的分屏功能(转)
    一些Python的惯用法和小技巧:Pythonic
    Docker(十五)-Docker的数据管理(volume/bind mount/tmpfs)
    Docker(十四)-Docker四种网络模式
    Docker(十三)-Docker save and load镜像保存
  • 原文地址:https://www.cnblogs.com/wenruo/p/12641878.html
Copyright © 2011-2022 走看看