我试图解决项目Euler problem 4,即:
回文数字两种方式相同。由两个2位数字的乘积制成的最大回文是9009 = 91×99。 找到由两个3位数字的乘积制成的最大回文。
这是我的解决方案,它的输出是997799,但这不是正确的答案,我想知道问题出在哪里:
package projecteuler;
public class Pro4 {
public static void main(String[] args) {
for(int i=999*999;i>=100*100;i--){
if(isPalindrome(i)==true){
System.out.println(i);
break;
}
}
}
static boolean isPalindrome(int x){
int[] bits = new int[7];
int index=1;
while(x>0){
bits[index]=x%10;
index++;
x/=10;
}
for(int i=1;i<=index/2;i++){
if(bits[i]!=bits[index-i]){
return false;
}
}
return true;
}
}
答案 0 :(得分:6)
这是一个不会遍历所有6位数字的解决方案:
public static boolean isPalindrome(int nr) {
int rev = 0; // the reversed number
int x = nr; // store the default value (it will be changed)
while (x > 0) {
rev = 10 * rev + x % 10;
x /= 10;
}
return nr == rev; // returns true if the number is palindrome
}
public static void main(String[] args) {
int max = -1;
for ( int i = 999 ; i >= 100 ; i--) {
for (int j = 999 ; j >= 100 ; j-- ) {
int p = i * j;
if ( max < p && isPalindrome(p) ) {
max = p;
}
}
}
System.out.println(max > -1? max : "No palindrome found");
}
修改强>
main
方法的改进解决方案(根据Peter Schuetze所说)可能是:
public static void main(String[] args) {
int max = -1;
for ( int i = 999 ; i >= 100 ; i--) {
if ( max >= i*999 ) {
break;
}
for (int j = 999 ; j >= i ; j-- ) {
int p = i * j;
if ( max < p && isPalindrome(p) ) {
max = p;
}
}
}
System.out.println(max > -1? max : "No palindrome found");
}
对于这个特殊的例子,时间大约是2倍,但如果你的数字更大,那么改进将会更加显着。
<强>输出强>:
906609
答案 1 :(得分:3)
您正在按顺序从999 * 999递减到100 * 100。这并不一定意味着您找到的第一个回文是两个3位数字的乘积。
回文997799有11和90709作为主要因素,不是两个3位数的乘积。
答案 2 :(得分:1)
for i
的for循环从998001下降到100000.你的程序中没有任何地方检查i
实际上是两个3位数字的乘积。
答案 3 :(得分:0)
JAVASCRIPT
嘿,我查看了一些答案,这很令人困惑,这就是我得到的:首先,我从一个按钮调用函数 getPalindrome(),我只给它数字的数量。然后在第一个 for 循环中,我通过添加 9 * 10^0 (9)、9 * 10^1 (90) 等将 max 设置为提供的数字的最大数字。然后我有两个嵌套循环,它们来自最后两个数字向下(例如 99 和 98)。第一个循环的条件大多无关紧要,因为最大的回文总是在最后一个数字中(例如 90 和 99、990 和 999 等)。在循环内部,我检查两个数字是否都不能被 11 整除,这意味着我们不能有回文,所以我只是跳过它并降低第二个数字。
如果其中之一可以被 11 整除,则调用回文函数检查。
尽管我不认为这个解决方案比其他解决方案更好/更快,但它更简单、更容易理解。
const getPalindrome = () => {
let max = 0;
for (let i = 0; i < digit; i++) {
max += 9 * Math.pow(10, i);
}
let min = (max + 1)/10;
let first = max;
let second = max - 1;
for (let i = first; i > min; i--) {
for (let j = second; j > min * 9; j--) {
if(i % 11 !== 0 && j % 11 !== 0) {
continue;
} else {
if(checkForPalindrome(i*j)) {
return setResult(i*j);
}
}
}
}
}
const checkForPalindrome = (num) => {
let digits = `${num}`;
for (let i = 0; i < Math.floor(digits.length / 2); i++) {
if(digits[i] !== digits[digits.length-1-i]) {
return false;
}
}
return true;
}
答案 4 :(得分:0)
这是Project_Euler-4问题的Python代码。
我们必须找到最大的回文数,它是两个三位数的乘积
import math
def isPal(x):
x=str(x)
t=x[::-1]
if(x==t):
return True
else:
return False
max=0
for i in range(999,99,-1):
for j in range(999,99,-1):
if(isPal(i*j)):
if((i*j)>max):
max=(i*j)
print(max)
答案将是906609
答案 5 :(得分:0)
#include <iostream>
using namespace std;
int reverse(int a){
int reverse=0;
for(int i=0;i<6;i++){
reverse = reverse*10+a%10;
a/=10;
}
return reverse;
}
int main(){
int a=999,max=1,rev;;
int b=999;
for(a=999;a>100;a--){
for(b=999;b>100;b--){
int p = a*b;
rev = reverse(p);
if (p==rev) {
if(max<rev){
max = rev;
}
}
}
}
cout<<"\n"<<max<<"\n";
return 0;
}
答案 6 :(得分:0)
此方法比以前的方法快得多。 它首先评估999 * 999.它是Puzzled over palindromic product problem
中提出的方法的实现我们想在较小的产品之前尝试更大的产品,所以接下来尝试998 * 998,外循环每次减少一个。在内循环中, 取外部限制数来创建(n + y)(n-y)(总是小于n ^ 2),迭代y直到其中一个因子太大或太小。
来自https://pthree.org/2007/09/15/largest-palindromic-number-in-python/, 其中一个因素必须是11的倍数。 检查其中一个因子是11的倍数,并且该产品是否大于之前找到的(或初始)回文数。
一旦满足这些测试,看看产品是否是回文。
一旦发现回文,我们可以将外环的限制提高到回文的平方根,因为这是可能是答案的最小值。
该算法仅在475次比较中找到了答案。这远远优于简单方法提出的810,000,甚至405450。
有人可以提出更快的方法吗?
Longest palindromes:
Max factor Max Palindrome
9999 99000099
99999 9966006699
999999 999000000999
9999999 99956644665999
99999999 9999000000009999
999999999 999900665566009999
public class LargestPalindromicNumberInRange {
private final long lowerLimit;
private final long upperLimit;
private long largestPalindrome;
private long largestFirstFactor;
private long largestSecondFactor;
private long loopCount;
private long answerCount;
public static void main(String[] args) {
long lowerLimit = 1000;
long upperLimit = 9999;
LargestPalindromicNumberInRange palindromicNumbers =
new LargestPalindromicNumberInRange(lowerLimit, upperLimit);
palindromicNumbers.TopDown();
}
private LargestPalindromicNumberInRange(long lowerLimit, long upperLimit){
this.lowerLimit = lowerLimit;
this.upperLimit = upperLimit;
}
private void TopDown() {
loopCount = 0;
answerCount = 0;
largestPalindrome = lowerLimit * lowerLimit;
long initialLargestPalindrome = largestPalindrome;
long lowerFactorLimit = lowerLimit;
for (long limit = upperLimit; limit > lowerFactorLimit; limit--){
for (long firstFactorValue = limit; firstFactorValue >= limit - 1; firstFactorValue--) {
long firstFactor = firstFactorValue;
long secondFactor = limit;
while(secondFactor <= upperLimit && firstFactor >= lowerLimit){
if (firstFactor % 11 == 0 || secondFactor % 11 == 0) {
long product = firstFactor * secondFactor;
if (product < largestPalindrome) { break; }
loopCount++;
if (IsPalindromic(product)) {
// System.out.print("Answer: " + product + "\n");
answerCount++;
largestPalindrome = product;
largestFirstFactor = firstFactor;
largestSecondFactor = secondFactor;
lowerFactorLimit = (long) Math.sqrt(largestPalindrome);
break;
}
}
firstFactor--;
secondFactor++;
}
}
System.out.print("Answer: " + largestPalindrome + "\n");
System.out.print("Factor1: " + largestFirstFactor + "\n");
System.out.print("Factor2: " + largestSecondFactor + "\n");
System.out.print("Loop count: " + loopCount + "\n");
System.out.print("Answer count: " + answerCount + "\n");
}
private boolean IsPalindromic(Long x) {
String forwardString = x.toString();
StringBuilder builder = new StringBuilder();
builder.append(forwardString);
builder = builder.reverse();
String reverseString = builder.toString();
return forwardString.equals(reverseString);
}
}
答案 7 :(得分:0)
另一个用C#编写的简单解决方案
private static void Main(string[] args)
{
var maxi = 0;
var maxj = 0;
var maxProd = 0;
for (var i = 999; i > 100; i--)
for (var j = 999; j > 100; j--)
{
var product = i * j;
if (IsPalindrome(product))
if (product > maxProd)
{
maxi = i;
maxj = j;
maxProd = product;
}
}
Console.WriteLine(
"The highest Palindrome number made from the product of two 3-digit numbers is {0}*{1}={2}", maxi, maxj,
maxProd);
Console.ReadKey();
}
public static bool IsPalindrome(int number)
{
var numberString = number.ToString();
var reverseString = string.Empty;
for (var i = numberString.Length - 1; i >= 0; --i)
reverseString += numberString[i];
return numberString == reverseString;
}
答案 8 :(得分:0)
找到由两个3位数字的乘积制成的最大回文。 R没有内置功能来检查回文,所以我创建了 一个虽然'rev'可以使用:)。此外,代码未针对进行优化 速度主要是为了提高可读性。
@Override
public boolean equals(Object obj) {
if (obj == this) {
return true;
}
if (obj == null || obj.getClass()!=getClass()) {
return false;
}
return Object.equals(this.getAlias(),((User) obj).getAlias())
&& Object.equals(this.getEmailAddress(),((User) obj).getEmailAddress())
&& Object.equals(this.getCellNumber(),((User) obj).getCellNumber()));
}
享受!
答案 9 :(得分:0)
/ * 找到由两个n位数字的乘积制成的最大回文。 由于结果可能非常大,您应该返回最大的回文模型1337。 例: 输入:2 输出:987 说明:99 x 91 = 9009,9009%1337 = 987 注意: n的范围是[1,8]。 * /
public class LargestPalindromeProduct {
public int largestPalindrome(int n) {
if(n<1 || n>8)
throw new IllegalArgumentException("n should be in the range [1,8]");
int start = (int)Math.pow(10, n-1); // n = 1, start 1, end = 10 -1. n = 2, start = 10, end = 99;
if(start == 1) start = 0 ; // n = 3, start = 100, end == 999
int end = (int)Math.pow(10, n) - 1;
long product = 0;
long maxPalindrome = 0;
for(int i = end ; i >= start ; i--)
{
for(int j = i ; j >= start ; j--)
{
product = i * j ;
// if one of the number is modulo 10, product can never be palindrome, e.g 100 * 200 = 200000, or 240*123 = 29520. this is because the product will always end with zero but it can never begin with zero except one/both of them numbers is zero.
if(product % 10 == 0)
continue;
if(isPalindrome(product) && product > maxPalindrome)
maxPalindrome = product;
}
}
return (int)(maxPalindrome % 1337);
}
public static boolean isPalindrome(long n){
StringBuffer sb = new StringBuffer().append(Long.toString(n)).reverse();
if(sb.toString().equals(Long.toString(n)))
return true;
return false;
}
public static void main(String[] args){
System.out.println(new LargestPalindromeProduct().largestPalindrome(2));
}
}
答案 10 :(得分:0)
在C中完成 这可能会对你有所帮助。
#include<stdio.h>
int calculate(int n)
{
int temp = 0,m = 0;
m = n;
while(n != 0)
{
temp = temp * 10;
temp = temp + n % 10;
n = n / 10;
}
if(m == temp)
{
printf(" %d \n",temp);
return temp;
}
else
{
return 0;
}
}
int main()
{
int i,j,temp = 0,count=0,temp1 = 0;
for(i = 100;i < 1000;i++)
{
for(j = 100;j < 1000;j++)
{
temp1 = i * j;
temp = calculate(temp1);
if(temp > count)
{
count = temp;
}
}
}
printf(" The Largest Palindrome number is : %d \n",count);
}
答案 11 :(得分:0)
我在这里看到很多错误。
我看到用户已经发布了正确的代码(ROMANIA)
答案 12 :(得分:0)
public class LargestPalindromProduct {
public static void main(String args[]) {
LargestPalindromProduct obj = new LargestPalindromProduct();
System.out.println("The largest palindrome for product of two 3-digit numbers is " + obj.getLargestPalindromeProduct(3));
}
/*
* @param digits
* @return
*/
private int getLargestPalindromeProduct(int digits) {
int largestPalindromeProduct = -1;
int startNum = (int)Math.pow(10, digits) - 1;
int endNum = (int)Math.pow(10, digits-1) - 1;
for (int i = startNum; i > endNum; i--) {
for (int j = startNum; j > endNum; j--) {
if (isPalindrome(i * j)) {
largestPalindromeProduct = Math.max(largestPalindromeProduct, i * j);
}
}
}
return largestPalindromeProduct;
}
private boolean isPalindrome(int number) {
String s = String.valueOf(number);
for (int i = 0, j = s.length() -1; i < j;i++, j--) {
if (s.charAt(i) != s.charAt(j)) {
return false;
}
}
return true;
}
答案 13 :(得分:0)
以上都没有给出正确的答案。 (我认为逻辑可能是正确的,但正确的答案是906609)。由于您不知道该数字是6位数还是5位数,因此您需要检查两者。下面是一个简单的代码来做同样的事情。
经常调用乘法,我知道......
i = 999
for u in range (100,1000):
for y in range (100,1000):
if len(str(u*y)) == 5 and str(u*y)[0]==str(u*y)[4]and str(u*y)[1]==str(u*y)[3] and u*y>i:
i=u*y
print ('the product of ', u, ' and ',y,' is: ',u*y)
elif len(str(u*y)) == 6 and str(u*y)[0]==str(u*y)[5]and str(u*y)[1]==str(u*y)[4]and str(u*y)[2]==str(u*y)[3]and u*y>i:
i=u*y
print ('the product of ', u, ' and ',y,' is: ',u*y)
答案 14 :(得分:0)
您还假设您找到的第一个回文最大。您找到的第一个回文是580085,这不是正确答案。
您还假设您找到的第一个回文是两个3位数字的乘积。您还应该使用两个不同的数字,而不是将999与999相乘,并向下迭代到100 * 100.
答案 15 :(得分:0)
您正在迭代循环,其编号从998001到10000,因为某些数字可能不是产品两个3位数字。
您应该乘以两个3位数字,然后比较它,如果该数字是回文与否。
你的for循环代码应该是:
for(int i=999;i>=100;i--)
{
int k = i-1;
int product = i * k;
System.out.println(i+" * "+k+" = "+product);
if(isPalindrome(product)==true){
System.out.println("palindrum number "+product);
System.out.println("Product of : "+i+" * "+k);
break;
}
}
这将为您提供最大的回文数,它是两位3位数的乘积 输出是:
palindrum number 289982
Product of : 539 * 538
如果你乘以两个数字不同,这都是正确的 如果您想要包含相同数量的产品以检查是否为回文,则上述代码可能几乎没有变化 该代码应该是:
for(int i=999;i>=100;i--){
int k = i;
int product = i * k;
System.out.println(i+" * "+k+" = "+product);
if(isPalindrome(product)==true){
System.out.println("palindrum number "+product);
System.out.println("Product of : "+i+" * "+k);
break;
}
else{
k = i - 1;
product = i * k;
System.out.println(i+" * "+k+" = "+product);
if(isPalindrome(product)==true){
System.out.println("palindrum number "+product);
System.out.println("Product of : "+i+" * "+k);
break;
}
}
}
为您提供如下输出:
palindrum number 698896
Product of : 836 * 836
我认为这是你需要做的。
答案 16 :(得分:-1)
#include <bits/stdc++.h>
using namespace std;
int main()
{
ios_base::sync_with_stdio(false);
cin.tie(NULL);
int sm=100,lr=999,ans=0;
for(int i=sm;i<=lr;i++) //for every number we traverse and find its
// product with other number
{
for(int j=sm;j<=lr;j++)
{
int pro=i*j; //find product of number
string str=to_string(pro); // convert to string
string rev = string(str.rbegin(),str.rend()); //reverse it
if(str==rev) //check it with
{ //string it is equal or
// with reverse
ans=max(ans,pro);} //storing only max value if it satisfy the
//condition
}
}
cout<<ans; // ans is 906609
return 0;
}