Python中的回文数
我正在尝试找出两个三位数相乘得到的最大回文数。在我去查找更高效的、而且更重要的是有效的解决方案之前,你能告诉我我的代码哪里出问题了吗?我总是得到一个空的结果。
def palindrome():
n = 100
m = 100
palind = []
while n<=999:
while m<=999:
prod = n * m
if str(prod) == str(prod)[::-1] and prod > palind[0]:
palind.pop(0)
palind.append(prod)
return palind
m = m + 1
n = n + 1
return palind
print palindrome()
6 个回答
这可能不是直接回答问题,但如果你想在某个范围内找回文数字,可以这样做:
def getPalindrome(lower, upper):
listPalind = []
for n in range(lower, upper):
if str(n) == str(n)[::-1]:
listPalind.append(n)
return listPalind
# Usage
print(getPalindrome(100, 300))
# Results
[101, 111, 121, 131, 141, 151, 161, 171, 181, 191, 202, 212, 222, 232, 242, 252, 262, 272, 282, 292]
这段代码是用来处理一些数据的。它的主要作用是从一个地方获取信息,然后对这些信息进行一些操作,最后把结果输出。具体来说,它可能会涉及到循环、条件判断等基本的编程概念。
在编程中,我们经常需要从一个数据源(比如数据库或文件)读取数据,然后对这些数据进行分析或修改。这个过程通常包括以下几个步骤:
1. **获取数据**:首先,我们需要从某个地方拿到数据。这可能是通过读取文件、查询数据库等方式。
2. **处理数据**:拿到数据后,我们会对这些数据进行一些操作,比如筛选出我们需要的信息,或者对数据进行计算。
3. **输出结果**:最后,我们会把处理后的结果展示出来,可能是打印到屏幕上,或者保存到文件中。
这段代码的具体实现可能会用到一些编程语言的基本语法,比如变量、函数、循环等。理解这些基本概念后,你就能更好地理解这段代码在做什么了。
def isPalindrome(self, x: int):
temp = 0
x1 = x
while x > 0:
y = x % 10
temp = temp * 10 + y
x = x//10
if(temp == x1):
return True
else:
return False
你没有在每次外层循环的迭代后重新设置
m = 100
。你提前返回了结果。把内层循环中的
return
语句去掉。最后的
return
语句不应该放在外层循环里面。你从来没有初始化过
palind
列表(感谢 @user2357112)。
建议:
不要用列表来保存最大的数字,简单的变量就够了。
在同一个表达式中,不需要把数字转换成字符串两次。可以把转换后的字符串存到一个变量里。
使用
range
函数来循环遍历数字。
如果我来写这个程序,我会这样做:
from itertools import product
def palindrome():
numbers, result = range(1000, 100, -1), -1
for num1, num2 in product(numbers, repeat = 2):
prod = num1 * num2
sprod = str(prod)
if sprod == sprod[::-1] and prod > result:
result = prod
return result
print palindrome() # 906609
这个快捷方式的作用是,当无法找到一个 i*j 大于已记录的最大值时,它能正确返回 906609(注意,如果你使用的是 Python 2,下面的代码对你有效,但你最好用 xrange
代替 range
,这样可以避免在内存中创建不必要的列表):
def palindrome(floor=0, upto=999):
'''
return the largest palindrome product for all number from (but not including)
floor to (and including) upto
'''
start = upto
largest = None
for i in range(start, floor, -1): # decreasing from upto
if i * upto < largest: # if True, impossible for higher product from combo
break
for j in range(start, i-1, -1): # decrease from upto to not including i-1
product = i*j
if str(product) == str(product)[::-1]:
if product > largest:
largest = product
return largest
用法:
>>> palindrome(99,999)
906609
>>> palindrome(10,13)
121
>>> palindrome(0,10)
9
这个快捷方式很重要,因为如果给一个非常大的数字,返回结果可能会花费很长时间:
>>> palindrome(upto=100000000)
9999000000009999L
我还创建了一个生成器,它会遍历从 0 到 999 的每一种组合,并且返回 906609。
def palindrome(upto=1000):
return max(i*j for i in range(upto) for j in range(upto)
if str(i*j) == str(i*j)[::-1])
但是当运行这个回文数时,如下所示:
>>> palindrome(upto=100000000)
完整的搜索会检查所有 100000000^2 的组合,耗时会非常长。
我最开始是这样写的,想着可以通过快捷方式避免遍历每一种可能的组合,但这样是错误的,它返回的是 888888:
def palindrome():
start = 999
largest = 0
for i in range(start, 0, -1): # decreasing from 999
if i * 999 < largest:
return largest
for j in range(start, i, -1): # decreasing from 999 to i
if str(i*j) == str(i*j)[::-1]:
largest = i*j
它首先计算 999 乘以 999,然后是 998 乘以 999,然后
998*998
997*999
997*998
997*997
...
但结果并不是单调递减的(也就是说,每个结果并不一定小于前一个结果)。
你有三个问题。
问题1:提前返回。
while n<=999:
while m<=999:
prod = n * m
if str(prod) == str(prod)[::-1] and prod > palind[0]:
palind.pop(0)
palind.append(prod)
# Here
return palind
m = m + 1
n = n + 1
# And here
return palind
一个 return
语句意味着这个函数现在就结束了。它会在当前位置停止,调用这个函数的地方会得到返回值,然后继续执行后面的代码。你不想在函数还没完成所有工作之前就这样结束。我们应该把 return
移到循环之后,也就是函数完成计算之后再返回。
问题2:palind[0]
没有初始化。
while n<=999:
while m<=999:
prod = n * m
# Here v
if str(prod) == str(prod)[::-1] and prod > palind[0]:
palind.pop(0)
palind.append(prod)
m = m + 1
n = n + 1
return palind
假设你的程序在运行时找到了第一个回文字符串。它试图把这个回文字符串和 palind[0]
进行比较,但 palind[0]
根本不存在!你需要先获取第一个回文字符串,而不是试图去比较一个不存在的值。我们来解决这个问题。
问题3:没有重置 m
。
palind = None
while n<=999:
while m<=999:
prod = n * m
if str(prod) == str(prod)[::-1]:
if palind is None or prod > palind:
palind = prod
m = m + 1
n = n + 1
return palind
在 n
循环的第一次迭代之后,你需要用 n=101
的值重新遍历所有可能的 m
值。但你没有这样做;你的代码把 m
保持在 1000
,所以它不会再进入内层循环。你可以手动重置 m
,但使用 for
循环会比 while
循环简单得多。解决了这三个问题后,你的代码看起来像这样:
palind = None
for n in xrange(100, 1000):
for m in xrange(100, 1000):
prod = n * m
if str(prod) == str(prod)[::-1]:
if palind is None or prod > palind:
palind = prod
return palind