Let's say a positive integer is a super-palindrome if it is a palindrome, and it is also the square of a palindrome.
Given two positive integers left
and right
represented as strings, return the number of super-palindromes integers in the inclusive range [left, right]
.
For example:
left = "4"
and right = "1000"
, the output should be 4 because 4, 9, 121, and 484 are superpalindromes. Note that 676 is not a superpalindrome: 26 * 26 = 676, but 26 is not a palindrome.left = "1"
and right = "2"
, the output should be 1.Write a function to solve this problem efficiently.
The problem asks us to find the number of super-palindromes within a given range [left, right]
. A super-palindrome is a number that is both a palindrome and the square of another palindrome.
A naive approach would involve iterating through all numbers in the range [left, right]
, checking if each number is a palindrome, and if so, checking if its square root is also a palindrome. This approach is highly inefficient.
Code (Python - Naive):
def is_palindrome(n):
s = str(n)
return s == s[::-1]
def naive_superpalindromes_in_range(left, right):
left_num = int(left)
right_num = int(right)
count = 0
for i in range(left_num, right_num + 1):
if is_palindrome(i):
sqrt_i = i**0.5
if sqrt_i == int(sqrt_i) and is_palindrome(int(sqrt_i)):
count += 1
return count
Time Complexity: O(N * sqrt(N)), where N is the size of the range (right - left + 1). Space Complexity: O(1)
Instead of checking every number in the range, we can generate palindromes and check if their squares are both within the range and are palindromes. Since the range is up to 10^18, the square root will be up to 10^9. We generate palindromes up to 10^9 and check their squares.
Code (Python - Optimal):
def is_palindrome(n):
s = str(n)
return s == s[::-1]
def generate_palindromes():
palindromes = []
for i in range(1, 100000):
s = str(i)
pal1 = s + s[::-1] # even length palindrome
pal2 = s + s[:-1][::-1] # odd length palindrome
palindromes.append(int(pal1))
palindromes.append(int(pal2))
return palindromes
def superpalindromes_in_range(left, right):
left_num = int(left)
right_num = int(right)
count = 0
palindromes = generate_palindromes()
for pal in palindromes:
sq = pal * pal
if left_num <= sq <= right_num and is_palindrome(sq):
count += 1
return count
Time Complexity: O(N), where N is the number of palindromes generated. Since we are generating palindromes up to 10^9, the number of palindromes generated is limited, making this approach much more efficient.
Space Complexity: O(N), where N is the number of palindromes generated. The space is used to store the list of generated palindromes.
long
in Java, int
in Python) to handle large numbers without overflow.left = "4", right = "1000"
The algorithm will generate palindromes, square them, and check if they fall in the range [4, 1000] and are also palindromes. The super-palindromes in this range are 4 (2x2), 9 (3x3), 121 (11x11), and 484 (22x22). Therefore, the output is 4.