【问题标题】:Project Euler #168 in Ruby; Has anyone gotten an answer?Ruby 中的欧拉计划 #168;有人得到答案了吗?
【发布时间】:2015-12-09 22:14:49
【问题描述】:

Project Euler problem #168。我的解决方案是:

num = (10..10**10).inject(0) do |sum,x| 
x.to_s.chars.rotate(-1).join.to_i % x == 0 ? sum += x : sum += 0
end
puts num.to_s[-5..-1].to_i

我正在处理的问题是我不知道这个“解决方案”是对还是错。当我尝试在终端上运行时,我没有收到错误消息或答案。看起来好像正在加载答案,但没有出现答案。

我认为这是因为数组太大了,那么我怎么能以另一种方式找到答案呢?我知道代码没有错误,因为我尝试了较小的范围,例如 10..10**6 并且它有效。

【问题讨论】:

  • 暴力破解无法解决这个问题。10^100 太大了。像大多数欧拉计划问题一样,必须利用一些“聪明的数学特性”。
  • 那么有没有其他方法可以解决这个问题?我只想知道答案lol
  • @JorgeLopezJr:我建议您在网上搜索一下以获取解释。欧拉计划是一个挑战,你应该尽自己的一份力——无论是解决问题还是研究已知的东西。 Stack Overflow 社区可能会在简单/幸运的情况下为您提供答案,但这不是保证。
  • @JorgeLopezJr,幸运的是,您需要查看的数字远少于 10**100 个。找出可以满足约束的数字模式。
  • 这个挑战的重点是这个数组太大而无法遍历每个元素。

标签: ruby algorithm range iteration


【解决方案1】:

具有这种右旋属性的数字具有以下形式:

ABCD and DABC = k*ABCD 

我们可以很容易地看到,k 应该小于 10,因为如果k 大于 10,k*ABCD 的位数将比 ABCD 多。

对于从19的每个k的个数,最高有效位(MSD)是aa from k to 9,我们可以找到满足X / k的最小数XX 的左旋转,X 的 MSD 是a

伪代码:

for(int k = 1; k < 10; k++){
   for(int a = k ; a < 10; a++){
       long X = 0;
       int cur = a;
       int mod = 0;
       do{
          X = X*10 + cur;
          cur = (mod*10 + cur)/k; //Result of this division is the next digit of X
          mod = (mod*10 + cur)%k; 
          if(pair <cur, mod> seen before)
             break;         
       }while(cur != a && mod != 0);
       //Notice that we will iterate less than 100 steps, as there is only 10*10 value of pair (cur, mod).
   }
}

我们注意到,所有数字 Y Y / k 是Y 的左旋转将具有XXXXXX... 的形式

所以,现在这项工作很简单,因为每个Y 将以X 结尾,只需保留X 的最后5 位数字并乘以有效Y 数字的数量(= 100 / 数量X 的数字)。

将所有这 5 位数字相加,我们将得到这个问题的答案。

【讨论】:

    猜你喜欢
    • 2023-03-16
    • 1970-01-01
    • 2011-04-11
    • 1970-01-01
    • 1970-01-01
    • 2022-12-09
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多