我如何检查数字是否是回文?
任何语言。任何算法。(使数字成为字符串然后反转字符串的算法除外)。
number
并is a palindrome
在上下文中表示什么:13E31(以10为底)怎么样?01210(前导零)?+ 10-10 + 1(五位数平衡三进制)?
我如何检查数字是否是回文?
任何语言。任何算法。(使数字成为字符串然后反转字符串的算法除外)。
number
并is a palindrome
在上下文中表示什么:13E31(以10为底)怎么样?01210(前导零)?+ 10-10 + 1(五位数平衡三进制)?
Answers:
这是欧拉计划的问题之一。当我在Haskell中解决该问题时,我完全按照您的建议做了,将数字转换为String。然后,检查该字符串是否为pallindrome变得很简单。如果它的性能足够好,那为什么还要麻烦使其更复杂呢?作为一个综合症是一种词汇性质,而不是一种数学性质。
to describe an algorithm to convert an integer to a string, which of course requires you to understand modulo
不 计算目标数字系统,能够增加会做(想想你如何从常用的十进制转换为二进制-用来思考的计算方法二进制并不意味着你不能这样做,例如,十进制算法(你可以做从二进制到十进制的转换,不进行除法或取模2)
对于任何给定的数字:
n = num;
rev = 0;
while (num > 0)
{
dig = num % 10;
rev = rev * 10 + dig;
num = num / 10;
}
如果n == rev
然后num
是回文:
cout << "Number " << (n == rev ? "IS" : "IS NOT") << " a palindrome" << endl;
num
after除法(较弱的键入)的分数的语言来实现,则需要这样做num = floor(num / 10)
。
在大多数答案中,有一个琐碎的问题是int变量可能会溢出。
请参阅http://articles.leetcode.com/palindrome-number/
boolean isPalindrome(int x) {
if (x < 0)
return false;
int div = 1;
while (x / div >= 10) {
div *= 10;
}
while (x != 0) {
int l = x / div;
int r = x % 10;
if (l != r)
return false;
x = (x % div) / 10;
div /= 100;
}
return true;
}
将每个数字推入堆栈,然后将其弹出。如果前后是相同的,那就是回文。
我没有注意到有没有使用任何额外空间来解决此问题的答案,即,我看到的所有解决方案都使用字符串或另一个整数来反转数字或其他一些数据结构。
尽管Java之类的语言会在整数溢出时回绕,但是C之类的语言中未定义此行为。(尝试在Java中反转2147483647(Integer.MAX_VALUE))
解决方法可能是使用long或类似方法,但从风格上讲,我不太喜欢那种方法。
现在,回文数的概念是该数应前后读相同。大。使用此信息,我们可以比较第一位数字和最后一位数字。技巧是,对于第一个数字,我们需要数字的顺序。比方说12321。将其除以10000将得到前导1。可以通过将mod取值为10来检索尾随的1。现在,将其减少到232 (12321 % 10000)/10 = (2321)/10 = 232
。现在,需要将10000减少2倍。因此,现在进入Java代码...
private static boolean isPalindrome(int n) {
if (n < 0)
return false;
int div = 1;
// find the divisor
while (n / div >= 10)
div *= 10;
// any number less than 10 is a palindrome
while (n != 0) {
int leading = n / div;
int trailing = n % 10;
if (leading != trailing)
return false;
// % with div gets rid of leading digit
// dividing result by 10 gets rid of trailing digit
n = (n % div) / 10;
// got rid of 2 numbers, update div accordingly
div /= 100;
}
return true;
}
根据Hardik的建议进行编辑,以涵盖数字为零的情况。
除了将数字设为字符串,然后反转字符串。
为什么要取消该解决方案?它易于实现且易于阅读。如果在没有手头电脑的情况下询问您是否2**10-23
是十进制回文,则可以通过将其写成十进制来进行测试。
至少在Python中,口号“字符串操作比算术慢”实际上是错误的。我将Smink的算术算法与简单的字符串反转进行了比较int(str(i)[::-1])
。速度没有显着差异-发生字符串反转的速度略快。
在编译语言(C / C ++)中,该口号可能成立,但其中一个风险就是大量溢出错误。
def reverse(n):
rev = 0
while n > 0:
rev = rev * 10 + n % 10
n = n // 10
return rev
upper = 10**6
def strung():
for i in range(upper):
int(str(i)[::-1])
def arithmetic():
for i in range(upper):
reverse(i)
import timeit
print "strung", timeit.timeit("strung()", setup="from __main__ import strung", number=1)
print "arithmetic", timeit.timeit("arithmetic()", setup="from __main__ import arithmetic", number=1)
结果以秒为单位(越低越好):
串入1.50960231881算术1.69729960569
我用一种蛮横的方式回答了欧拉问题。自然,当我进入新的未锁定的相关论坛主题时,会显示出更智能的算法。即,一个由Begoner操纵的成员使用了一种新颖的方法,以至于我决定使用他的算法重新实现我的解决方案。他的版本是Python(使用嵌套循环),而我在Clojure中重新实现了(使用单个循环/递归)。
在这里为您娱乐:
(defn palindrome? [n]
(let [len (count n)]
(and
(= (first n) (last n))
(or (>= 1 (count n))
(palindrome? (. n (substring 1 (dec len))))))))
(defn begoners-palindrome []
(loop [mx 0
mxI 0
mxJ 0
i 999
j 990]
(if (> i 100)
(let [product (* i j)]
(if (and (> product mx) (palindrome? (str product)))
(recur product i j
(if (> j 100) i (dec i))
(if (> j 100) (- j 11) 990))
(recur mx mxI mxJ
(if (> j 100) i (dec i))
(if (> j 100) (- j 11) 990))))
mx)))
(time (prn (begoners-palindrome)))
也有Common Lisp的答案,但对我来说这些答案是不可理解的。
这是一个Scheme版本,该版本构造了可以针对任何基础工作的函数。它具有冗余检查:如果该数字是底数的倍数(以0结尾),则快速返回false。
而且它不会重建整个倒数,只有一半。
这就是我们所需要的。
(define make-palindrome-tester
(lambda (base)
(lambda (n)
(cond
((= 0 (modulo n base)) #f)
(else
(letrec
((Q (lambda (h t)
(cond
((< h t) #f)
((= h t) #t)
(else
(let*
((h2 (quotient h base))
(m (- h (* h2 base))))
(cond
((= h2 t) #t)
(else
(Q h2 (+ (* base t) m))))))))))
(Q n 0)))))))
常量因子比@sminks方法好一点的方法:
num=n
lastDigit=0;
rev=0;
while (num>rev) {
lastDigit=num%10;
rev=rev*10+lastDigit;
num /=2;
}
if (num==rev) print PALINDROME; exit(0);
num=num*10+lastDigit; // This line is required as a number with odd number of bits will necessary end up being smaller even if it is a palindrome
if (num==rev) print PALINDROME
要检查给定的编号是否为回文式(Java代码)
class CheckPalindrome{
public static void main(String str[]){
int a=242, n=a, b=a, rev=0;
while(n>0){
a=n%10; n=n/10;rev=rev*10+a;
System.out.println(a+" "+n+" "+rev); // to see the logic
}
if(rev==b) System.out.println("Palindrome");
else System.out.println("Not Palindrome");
}
}
此处发布的许多解决方案都将整数取反,并将其存储在使用额外空间的变量中,该变量为O(n)
,但这是带O(1)
空间的解决方案。
def isPalindrome(num):
if num < 0:
return False
if num == 0:
return True
from math import log10
length = int(log10(num))
while length > 0:
right = num % 10
left = num / 10**length
if right != left:
return False
num %= 10**length
num /= 10
length -= 2
return True
试试这个:
reverse = 0;
remainder = 0;
count = 0;
while (number > reverse)
{
remainder = number % 10;
reverse = reverse * 10 + remainder;
number = number / 10;
count++;
}
Console.WriteLine(count);
if (reverse == number)
{
Console.WriteLine("Your number is a palindrome");
}
else
{
number = number * 10 + remainder;
if (reverse == number)
Console.WriteLine("your number is a palindrome");
else
Console.WriteLine("your number is not a palindrome");
}
Console.ReadLine();
}
}
public class Numbers
{
public static void main(int givenNum)
{
int n= givenNum
int rev=0;
while(n>0)
{
//To extract the last digit
int digit=n%10;
//To store it in reverse
rev=(rev*10)+digit;
//To throw the last digit
n=n/10;
}
//To check if a number is palindrome or not
if(rev==givenNum)
{
System.out.println(givenNum+"is a palindrome ");
}
else
{
System.out.pritnln(givenNum+"is not a palindrome");
}
}
}
checkPalindrome(int number)
{
int lsd, msd,len;
len = log10(number);
while(number)
{
msd = (number/pow(10,len)); // "most significant digit"
lsd = number%10; // "least significant digit"
if(lsd==msd)
{
number/=10; // change of LSD
number-=msd*pow(10,--len); // change of MSD, due to change of MSD
len-=1; // due to change in LSD
} else {return 1;}
}
return 0;
}
递归的方式,不是很有效,只是提供一个选择
(Python代码)
def isPalindrome(num):
size = len(str(num))
demoninator = 10**(size-1)
return isPalindromeHelper(num, size, demoninator)
def isPalindromeHelper(num, size, demoninator):
"""wrapper function, used in recursive"""
if size <=1:
return True
else:
if num/demoninator != num%10:
return False
# shrink the size, num and denominator
num %= demoninator
num /= 10
size -= 2
demoninator /=100
return isPalindromeHelper(num, size, demoninator)