寻找吸血鬼数量从10到100万

时间:2014-02-05 16:20:56

标签: c loops infinite-loop nested-loops

我是一名新的C学习者,并试图将吸血鬼数量从10万增加到100万。

吸血鬼号码: http://en.wikipedia.org/wiki/Vampire_number

代码准备就绪但是,它不能正常工作。它只是继续搜索很长一段时间没有打印任何东西,一段时间后打印大量的数字。我无法弄清楚问题是什么,这就是代码:

#include <stdio.h>
#include <math.h>
#include <string.h>
#include <stdlib.h>

#define true 1
#define false 0

int main(void){
   int i,j,t,s,m,n,counter=0;

   for(i=10; i<100; i++){
      m = Control2Digits(i);
      if(m == true){
         counter++;
         printf("%d.Vampire number: %d \n", counter, i);
      }
   }

   for(j=1000; j<10000; j++){
     m = Control4Digits(j);
     if(m == true){
         counter++;
         printf("%d.Vampire number: %d \n", counter , j);
      }
   }

   for(t=100000; t<1000000; t++){
      for(s=100000; s<1000000; s++){
         m = Control6Digits(s,t);
         if(m == true){
            n = (s*t);
            counter++;
            printf("%d.Vampire number: %d \n", counter, n);
         }
      }
   }
}

int Control2Digits(int number){
   int n1,n2;

   n1 = number%10;
   n2 = (number-n1)/10;

   if(n1*n2 == number)
      return true;

   return false;

}

int calculate4(int s1, int s2, int s3, int s4){
   int p1,p2;
   p1 = (s1*10)*s2;
   p2 = (s3*10)*s4;
   return (p1*p2);
}

int Control4Digits(int number){

   int g1,g2;
   int t1,t2,t3,t4;

   if(number%100 == 0)
      return false;

   g1 = number/100;
   g2 = number%100;
   t1 = g1/10;
   t2 = g1%10;
   t3 = g2/10;
   t4 = g2%10;

   if(calculate4(t1,t2,t3,t4) == number)
      return true;
   else if(calculate4(t2,t1,t3,t4) == number)
      return true;
   else if(calculate4(t2,t1,t4,t3) == number)
      return true;
   else if(calculate4(t1,t2,t4,t3) == number)
      return true;
   else if(calculate4(t1,t3,t2,t4) == number)
      return true;
   else if(calculate4(t3,t1,t2,t4) == number)
      return true;
   else if(calculate4(t1,t4,t2,t3) == number)
      return true;
   else if(calculate4(t1,t3,t4,t2) == number)
      return true;
   else if(calculate4(t4,t1,t2,t3) == number)
      return true;
   else if(calculate4(t3,t1,t4,t2) == number)
      return true;
   else if(calculate4(t1,t4,t3,t2) == number)
      return true;
   else if(calculate4(t4,t1,t3,t2) == number)
      return true;

   return false;

}

int Control6Digits(int num1, int num2){
   long int k,l,m,n,c;
   k = num1%10;
   l = num2%10;

   if(k + l == 0)
      return false;
   else{
      m = (num1*num2);
      n = (num1*1000+num2);

      if(a == g)
         return true;
      c = true;
   }

   return false;
}

3 个答案:

答案 0 :(得分:1)

变化:

p2 = (s3*10)*s3;

要:

p2 = (s3*10)*s4;

另一小段建议:在代码中的所有位置将intlong更改为unsigned long long,以防止大输入的计算溢出。

答案 1 :(得分:1)

int calculate4(int s1, int s2, int s3, int s4) {
   int p1,p2;
   p1 = (s1*10)+s2;
   p2 = (s3*10)+s4;
   return (p1*p2);
}

您正在使用*而不是+

重建这两个部分

然后你得到了例子

    1.Vampire number: 1260
    2.Vampire number: 1395
    3.Vampire number: 1435
    4.Vampire number: 1530
    5.Vampire number: 1827
    6.Vampire number: 2187
    7.Vampire number: 6880

答案 2 :(得分:1)

Beer Baron已经指出了你的四位数吸血鬼数字的错误。

您的六位数字的逻辑未正确实施且也不清楚。 (在发布状态下,它将无法编译:什么是a,什么是g?)如果您遵循四位数代码的逻辑,则必须检查360组合每个数字,都有点多。

另外,我希望您的代码执行时间过长并不会感到惊讶:您有两个嵌套循环,从100,000到100万,即每个900,000。这是810亿次迭代。

您的四位数代码原则上有效,如果您想检查吸血鬼的单个数字,则可以。如果你想识别某个范围的所有吸血鬼号码,你应该使用“传播”方法:不要将v = a * b从1,000迭代到10,000,而是为a和{{1}尝试两个嵌套循环从10到100.(b不必每次从10开始。例如,如果b为20,则从a开始就足够了,因为任何产品都是较低的50将有较少的数字。)

(这种方法有点像使用用于查找素数的Sieve of erathostenes。它不一样,因为你仍然需要测试你的嫌疑人。这个解决方案的一个缺点是你不会在升序中找到你的吸血鬼数字例如,您会在b之前找到1395 == 15 * 93。如果您的数字必须订购,请将它们存储在一个数组中并在打印前对其进行排序。)

您现在必须想出一种比较数字的有效方法。一个简单的解决方案是为每个数字提供一个带有计数器的数组。从所有计数器等于零开始,添加可疑吸血鬼号码的数字,减去f牙的数字,如果你最后再次全部为零,你就找到了一个吸血鬼号码。

另一个解决方案是将所谓的吸血鬼号码打印到一个字符串,将两个f牙打印到另一个字符串,按字符排序并比较它们。

您可能也可能使用位掩码,但由于数字的计数也必须匹配,因此仅为某些数字设置位是不够的。对于最多一百万的数字,您可以为数字1260 == 21 * 60添加8的幂,例如8 ^ 3。

我喜欢的方法是使用素数乘积来识别数字。你必须注意整数溢出,但对于最多一百万的数字,你是安全的:

3

然后你可以像这样测试f牙和数字:

typedef unsigned int uint;

uint fact(uint a)
{
    static uint primes[10] = {2, 3, 5, 7, 11, 13, 17, 23, 29, 31};
    uint r = 1u;

    while (a) {
        r *= primes[a % 10];
        a /= 10;
    }

    return r;
}