classSolution: deflargestPalindrome(self, n: int) -> int: if n == 1: return9 upper = 10 ** n - 1 for left inrange(upper, upper // 10, -1): # 枚举回文数的左半部分 p, x = left, left while x: p = p * 10 + x % 10# 翻转左半部分到其自身末尾,构造回文数 p x //= 10 x = upper while x * x >= p: if p % x == 0: # x 是 p 的因子 return p % 1337 x -= 1
classSolution { public: intlargestPalindrome(int n){ if (n == 1) { return9; } int upper = pow(10, n) - 1; for (int left = upper;; --left) { // 枚举回文数的左半部分 long p = left; for (int x = left; x > 0; x /= 10) { p = p * 10 + x % 10; // 翻转左半部分到其自身末尾,构造回文数 p } for (long x = upper; x * x >= p; --x) { if (p % x == 0) { // x 是 p 的因子 return p % 1337; } } } } };
classSolution { publicintlargestPalindrome(int n) { if (n == 1) { return9; } intupper= (int) Math.pow(10, n) - 1; intans=0; for (intleft= upper; ans == 0; --left) { // 枚举回文数的左半部分 longp= left; for (intx= left; x > 0; x /= 10) { p = p * 10 + x % 10; // 翻转左半部分到其自身末尾,构造回文数 p } for (longx= upper; x * x >= p; --x) { if (p % x == 0) { // x 是 p 的因子 ans = (int) (p % 1337); break; } } } return ans; } }
publicclassSolution { publicintLargestPalindrome(int n) { if (n == 1) { return9; } int upper = (int) Math.Pow(10, n) - 1; int ans = 0; for (int left = upper; ans == 0; --left) { // 枚举回文数的左半部分 long p = left; for (int x = left; x > 0; x /= 10) { p = p * 10 + x % 10; // 翻转左半部分到其自身末尾,构造回文数 p } for (long x = upper; x * x >= p; --x) { if (p % x == 0) { // x 是 p 的因子 ans = (int) (p % 1337); break; } } } return ans; } }
[sol1-Golang]
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
funclargestPalindrome(n int)int { if n == 1 { return9 } upper := int(math.Pow10(n)) - 1 for left := upper; ; left-- { // 枚举回文数的左半部分 p := left for x := left; x > 0; x /= 10 { p = p*10 + x%10// 翻转左半部分到其自身末尾,构造回文数 p } for x := upper; x*x >= p; x-- { if p%x == 0 { // x 是 p 的因子 return p % 1337 } } } }
[sol1-C]
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
intlargestPalindrome(int n){ if (n == 1) { return9; } int upper = pow(10, n) - 1; for (int left = upper;; --left) { // 枚举回文数的左半部分 long p = left; for (int x = left; x > 0; x /= 10) { p = p * 10 + x % 10; // 翻转左半部分到其自身末尾,构造回文数 p } for (long x = upper; x * x >= p; --x) { if (p % x == 0) { // x 是 p 的因子 return p % 1337; } } } }
[sol1-JavaScript]
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
var largestPalindrome = function(n) { if (n === 1) { return9; } const upper = 10 ** n - 1; for (let left = upper; left > upper / 10; left--) { let right = String(left).split('').reverse().join(''); let p = BigInt(String(left) + right) //得到回文数 let x = BigInt(upper); while (x * x >= p) { if (p % x === BigInt(0)) { // x 是 p 的因子 return p % BigInt(1337); } x--; } } };
复杂度分析
时间复杂度:O(10^{2n})。枚举 left 和 x 的时间复杂度均为 O(10^n)。实际上我们只需要枚举远小于 10^n 个的 left 就能找到答案,实际的时间复杂度远低于 O(10^{2n})。