鱼C论坛

 找回密码
 立即注册
查看: 2795|回复: 14

题目57:考察2的平方根的展开

[复制链接]
发表于 2015-6-18 23:37:22 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x

Square root convergents

It is possible to show that the square root of two can be expressed as an infinite continued fraction.

√ 2 = 1 + 1/(2 + 1/(2 + 1/(2 + ... ))) = 1.414213...

By expanding this for the first four iterations, we get:

1 + 1/2 = 3/2 = 1.5
1 + 1/(2 + 1/2) = 7/5 = 1.4
1 + 1/(2 + 1/(2 + 1/2)) = 17/12 = 1.41666...
1 + 1/(2 + 1/(2 + 1/(2 + 1/2))) = 41/29 = 1.41379...

The next three expansions are 99/70, 239/169, and 577/408, but the eighth expansion, 1393/985, is the first example where the number of digits in the numerator exceeds the number of digits in the denominator.

In the first one-thousand expansions, how many fractions contain a numerator with more digits than denominator?


题目:

2 的平方根可以被表示为无限延伸的分数:

√ 2 = 1 + 1/(2 + 1/(2 + 1/(2 + ... ))) = 1.414213...

将其前四次迭代展开,我们得到:

1 + 1/2 = 3/2 = 1.5
1 + 1/(2 + 1/2) = 7/5 = 1.4
1 + 1/(2 + 1/(2 + 1/2)) = 17/12 = 1.41666...
1 + 1/(2 + 1/(2 + 1/(2 + 1/2))) = 41/29 = 1.41379...

接下来三次迭代的展开是 99/70, 239/169, 和 577/408, 但是第八次迭代的展开, 1393/985, 是第一个分子的位数超过分母的位数的例子。

在前 1000 次迭代的展开中,有多少个的分子位数超过分母位数?

想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2016-8-31 20:02:20 | 显示全部楼层
153..
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2016-9-29 03:52:59 | 显示全部楼层
  1. 完全正确
  2. 153
  3. [Finished in 0.1s]

  4. fenmu, fenzi, count = [2], [3], 0
  5. for i in range(1,1000):
  6.         fenmu.append (fenzi[i-1]+fenmu[i-1])
  7.         fenzi.append (fenmu[i]+fenmu[i-1])
  8. for j in range(1000):
  9.         if len(str(fenzi[j])) > len(str(fenmu[j])):
  10.                 count += 1
  11. print (count)
复制代码
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 1 反对 0

使用道具 举报

发表于 2016-11-22 10:38:51 | 显示全部楼层
  1. from fractions import Fraction
  2. count = 0
  3. for i in range(1,1001):
  4.     temp = 2+Fraction(1,2)
  5.     while i:
  6.         if i ==1:
  7.             temp = 1+1/temp
  8.         else:
  9.             temp = 2+1/temp
  10.         i -= 1
  11.     (a,b) = str(temp).split('/')
  12.     if len(a) > len(b):
  13.         count += 1
  14. print(count)
复制代码

结果:153.
很慢
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2017-1-17 16:11:07 | 显示全部楼层
  1. # encoding:utf-8
  2. # 考察2的平方根展开
  3. from time import time
  4. def euler057(N=1000000):
  5.     a, b = 1, 2
  6.     count = 0
  7.     for i in range(1, 1000):
  8.         a, b = b, a + 2 * b
  9.         if len(str(a + b)) > len(str(b)):
  10.             # print(a+b,b,(a+b)/b)
  11.             count += 1
  12.     print(count)
  13. if __name__ == '__main__':
  14.     start = time()
  15.     euler057()
  16.     print('cost %.6f sec' % (time() - start))
复制代码

153
cost 0.006001 sec
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2017-1-21 20:38:04 | 显示全部楼层
1,    1+1/2
2,    1+2/5      1+2/(2*2+1)
3,    1+5/12    1+5/(2*5+2)
4,    1+12/29  1+12/(2*12+5)
......
以此类推
  1. from time import time
  2. ttt = time()
  3. N, count, n, m = 1, 0, 1, 2
  4. while N <= 1000:
  5.     n, m = m, m*2 + n
  6.     if len(str(n+m)) > len(str(m)):
  7.         count += 1
  8.     N += 1
  9. print(count, time()-ttt)
复制代码
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2017-6-17 00:16:30 | 显示全部楼层
本帖最后由 渡风 于 2017-6-17 00:19 编辑

此代码使用matlab编程
Problem57所用时间为: 3.1446秒
Problem57的答案为: 153
  1. %% Problem57.m
  2. % 最后编辑时间:17-06-17 0:02
  3. % 问题:考察2的平方根的展开
  4. %事实上可以先求出小于等于100w的数,然后用总数减去之
  5. % Problem57所用时间为: 3.1446秒
  6. % Problem57的答案为: 153

  7. function Output = Problem57()
  8. tic

  9. Total = 0;
  10. Demo = 2; %分母
  11. Elem = 3; %分子

  12. for ii = 1:999
  13.     NewEl = Vector_Plus(Vector_Plus(Demo,Demo), Elem);
  14.     NewDe = Vector_Plus(Demo, Elem);
  15.     if length(NewEl) >  length(NewDe)
  16.         Total = Total + 1;
  17.     end
  18.     disp(Demo)
  19.     Demo = NewDe;
  20.     Elem = NewEl;
  21. end
  22.    
  23. Output = Total;   
  24.                      
  25. toc
  26. disp('此代码使用matlab编程')
  27. disp(['Problem57所用时间为: ',num2str(toc),'秒'])
  28. disp(['Problem57的答案为: ',num2str(Output)])
  29. end
  30. %此程序实现两个向量的加法
  31. function Output=Vector_Plus(a,b)
  32. if nargin==0
  33.     a=[9 9 9 9 9 9 ];
  34.     b=[2 0];
  35. end
  36. L1=length(a);
  37. L2=length(b);
  38. L=max(L1,L2);
  39. if L1<L2
  40.    Span=L2-L1;
  41.    Newa=[zeros(1,Span),a];
  42.    Newb=b;
  43. elseif L1>L2
  44.    Span=L1-L2;
  45.    Newa=a;
  46.    Newb=[zeros(1,Span),b];
  47. else
  48.     Newa=a;
  49.     Newb=b;
  50. end
  51. Rank=Newa+Newb;
  52. for ii=L:-1:2
  53.     if Rank(ii)>=10
  54.         Rank(ii)=Rank(ii)-10;
  55.         Rank(ii-1)=Rank(ii-1)+1;
  56.     end
  57. end
  58. Biggest=0;
  59. while (Rank(1)>=10)
  60.     if Rank(1)>=10
  61.        Rank(1)=Rank(1)-10;
  62.        Biggest=Biggest+1;
  63.     end
  64. end
  65. if Biggest>0
  66.     Output=[Biggest,Rank];
  67. else
  68.     Output=Rank;
  69. end
  70. end
  71.         
  72.    
复制代码
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2017-10-1 18:19:23 | 显示全部楼层
用的matlab
结果是:
   153

时间已过 0.016199 秒。
>>
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2018-8-1 20:47:27 | 显示全部楼层
import time
from fractions import Fraction


def time_it():
        start=time.time()
        fun()
        end=time.time()
        print('cost %.6f Secs'%(end-start))


def get_root(time):
        n=1
        m=2
        for i in range(time):
                f=Fraction(n,m)
                n,m=m,2*m+n
        return 1+f


def fun():
        sum_f=1
        count=0
        list_num=[]
        for i in range(1,1001):
                f= get_root(i)
                numerator=f.numerator
                denominator=f.denominator
                if len(str(numerator)) > len(str(denominator)):#分子位数超过分母位数
                        count+=1
                        list_num.append(f)
        print('前1000次迭代中,有%d次迭代中分子位数超过分母位数'%count)


if __name__=='__main__':
        time_it()

'''
前1000次迭代中,有153次迭代中分子位数超过分母位数
cost 4.505202 Secs
'''
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2019-6-26 09:37:50 | 显示全部楼层
Fib 数列问题

计数:153 次
用时:0.156001 秒

  1. import time

  2. def Fib(N, a, b):
  3.     n, a, b = 0, a, b
  4.     while n < N:
  5.         yield a
  6.         a, b = b,  2*b + a
  7.         n += 1


  8. def cal_result():
  9.     count = 0
  10.     fenzi = [_ for _ in Fib(1000, 3, 7)]
  11.     fenmu = [_ for _ in Fib(1000, 2, 5)]
  12.     for i in range(1000):
  13.         if len(str(fenzi[i])) > len(str(fenmu[i])):
  14.             count += 1
  15.     return count
  16. print("计数:{} 次\n用时:{} 秒".format(cal_result(), time.process_time()))
复制代码
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2019-7-23 18:55:26 | 显示全部楼层
本帖最后由 永恒的蓝色梦想 于 2021-1-13 12:33 编辑
  1. nume = 1
  2. deno = 2
  3. count = 0

  4. for _ in range(1, 1000):
  5.     nume, deno = deno, nume + 2 * deno
  6.     count += len(str(nume + deno)) > len(str(deno))

  7. print(count)
复制代码
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2020-8-21 19:31:45 | 显示全部楼层
153

Process returned 0 (0x0)   execution time : 0.061 s
Press any key to continue.
重载了+运算的高精度
  1. #include<iostream>
  2. #include<vector>
  3. using namespace std;

  4. typedef struct BigInt{
  5.   vector<int> v;

  6.   BigInt(vector<int> v):v(v){}
  7. }BI;

  8. BI operator + (const BI & a,const BI & x){
  9.   vector<int> t1 = a.v;
  10.   vector<int> t2 = x.v;
  11.   if (a.v.size() < x.v.size())  swap(t1,t2);

  12.   for (int i = 0;i < max(t1.size(),t2.size() );i++){
  13.       if (i < t2.size())  t1[i] += t2[i];
  14.       if (i > 0 && t1[i-1] > 9)  {t1[i]++;  t1[i-1] -= 10;}
  15.   }

  16.   if (t1[t2.size()-1] > 9)
  17.     if (t1.size() == t2.size() )  {t1.push_back(1);  t1[t1.size()-2] -= 10;}

  18.     else {
  19.       t1[t2.size()]++;
  20.       for (int i = t2.size();i < t1.size()-1;i++){
  21.         if (t1[i] > 9) {t1[i] -= 10;  t1[i+1]++;}
  22.         else break;
  23.       }
  24.       t1[t2.size()-1] -= 10;
  25.     }
  26.   return BI(t1);
  27. }

  28. int main(){
  29.   int cnt = 0;
  30.   vector<int> a(1,1),b(2,1);
  31.   BI n(a),d(b);

  32.   for (int i = 0;i < 1000;i++){
  33.     BI t = n;
  34.     n = d;
  35.     d = t + d + d;

  36.     BI u = n + d;
  37.     if (u.v.size() > d.v.size())  cnt++;
  38.   }
  39.   cout << cnt << endl;
  40.   return 0;
  41. }
复制代码
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2020-10-28 21:27:07 | 显示全部楼层
用时
  1. from time import time

  2. t = time()
  3. a = 3  #a是分子
  4. b = 2  #b是分母
  5. l1 = []
  6. count = 1000
  7. while count:
  8.     c = b #上一个数的分母
  9.     b = a+b
  10.     a = b+c
  11.     if len(str(a))>len(str(b)):
  12.         l1.append((a,b))
  13.     count -= 1
  14.    
  15. print(l1,'\n')
  16. print('用时%.6f sec,满足的数字有%d 个.' % (time()-t,len(l1)))
复制代码
0.373784 sec,满足的数字有153 个.应该是电脑问题,不然肯定要快一点。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2022-1-9 10:49:17 | 显示全部楼层
本帖最后由 guosl 于 2022-1-9 11:05 编辑

从这题开始,有一些列的题目都牵涉到了连分数,连分数的内容可以参考《初等数论》(闵嗣鹤 严士健编)一书。
对于一个连分数[a1,a2,...ak...],若假设p(k)/q(k)为其的第k个渐进分数,则有:
p(1)=a1,p(2)=a2*a1+1,...,p(k)=ak*p(k-1)+p(k-2),...
q(1)=1,q(2)=a2,...,q(k)=ak*q(k-1)+q(k-2),...
对于本题则连分数为:[1,2,...,2,...]是一个无限循环的连分数。套用前面给出的公式再结合mpir库,本题就非常简单了。
  1. /*
  2. 答案:153
  3. */
  4. #include <iostream>
  5. #include <string>
  6. #include <mpirxx.h>
  7. using namespace std;

  8. int main(void)
  9. {
  10.   mpz_class p0 = 1, p1 = 3, p2;
  11.   mpz_class q0 = 1, q1 = 2, q2;
  12.   int nCount = 0;
  13.   for (int i = 2; i <= 1000; ++i)
  14.   {
  15.     p2 = 2 * p1 + p0;
  16.     q2 = 2 * q1 + q0;
  17.     string sp = p2.get_str();
  18.     string sq = q2.get_str();
  19.     if (sp.length() > sq.length())
  20.       ++nCount;
  21.     p0 = p1;
  22.     p1 = p2;
  23.     q0 = q1;
  24.     q1 = q2;
  25.   }
  26.   cout << nCount << endl;
  27.   return 0;
  28. }
复制代码
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2022-8-8 17:20:32 | 显示全部楼层
  1. use std::time::Instant;

  2. fn main() {
  3.     let now = Instant::now();
  4.     // Copy from "[飘飞的白杨](https://fishc.com.cn/space-uid-359393.html)"
  5.     let (mut num, mut n, mut m) = (0, 1, 2);
  6.     for _ in 0..1001 {
  7.         (n, m) = (m, m * 2 + n);
  8.         if (n + m).to_string().len() > m.to_string().len() {
  9.             num += 1;
  10.         }
  11.     }
  12.     println!("{}", num);
  13.     println!("[Finished in {}s]", now.elapsed().as_secs_f32())
  14. }
复制代码

319
[Finished in 0.0004963s]
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2024-4-27 21:55

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表