分母と分子を別計算にしながら、途中でRationalを使って桁数を抑えることで単純な加算より時間は短くなりました。
参考まで。
Ruby
1 MAX = ARGV [ 0 ] . to_i
2 RAT_NUM = 1070
3
4 puts "float simple addition"
5 sum = 0.0
6 wer = 1
7 n = 0
8 stime = Time . now
9 while wer <= MAX do
10 n + = 1
11 sum + = 1.0 / n
12 if sum > wer then
13 printf ( "wer=%2d, n=%10d, sum=%.15e, elapse=%f\n" , wer , n , sum , Time . now - stime )
14 wer + = 1
15 end
16 end
17
18 puts "rational nume/deno addition"
19 deno = 1
20 nume = 0
21 wer = 1
22 n = 0
23 stime = Time . now
24 while wer <= MAX do
25 n + = 1
26 nume = nume * n + deno
27 deno * = n
28 if nume > wer * deno then
29 sum = Rational ( nume , deno )
30 printf ( "wer=%2d, n=%10d, sum=%.15e, elapse=%f\n" , wer , n , sum . to_f , Time . now - stime )
31 wer + = 1
32 nume = sum . numerator
33 deno = sum . denominator
34 elsif n % RAT_NUM == 0 then
35 sum = Rational ( nume , deno )
36 nume = sum . numerator
37 deno = sum . denominator
38 end
39 end
40
41 puts "rational simple addition"
42 sum = Rational ( 0 )
43 wer = 1
44 n = 0
45 stime = Time . now
46 while wer <= MAX do
47 n + = 1
48 sum + = Rational ( 1 , n )
49 if sum > wer then
50 printf ( "wer=%2d, n=%10d, sum=%.15e, elapse=%f\n" , wer , n , sum . to_f , Time . now - stime )
51 wer + = 1
52 end
53 end
54
55 float simple addition
56 wer = 1 , n = 2 , sum = 1.500000000000000e+00 , elapse = 0.000000
57 wer = 2 , n = 4 , sum = 2.083333333333333e+00 , elapse = 0.001000
58 wer = 3 , n = 11 , sum = 3.019877344877345e+00 , elapse = 0.001000
59 wer = 4 , n = 31 , sum = 4.027245195436520e+00 , elapse = 0.002002
60 wer = 5 , n = 83 , sum = 5.002068272680166e+00 , elapse = 0.002002
61 wer = 6 , n = 227 , sum = 6.004366708345567e+00 , elapse = 0.003019
62 wer = 7 , n = 616 , sum = 7.001274097134162e+00 , elapse = 0.003019
63 wer = 8 , n = 1674 , sum = 8.000485571995782e+00 , elapse = 0.003993
64 wer = 9 , n = 4550 , sum = 9.000208062931115e+00 , elapse = 0.003993
65 wer = 10 , n = 12367 , sum = 1.000004300827578e+01 , elapse = 0.004990
66 wer = 11 , n = 33617 , sum = 1.100001770863642e+01 , elapse = 0.006985
67 wer = 12 , n = 91380 , sum = 1.200000305166562e+01 , elapse = 0.012998
68 wer = 13 , n = 248397 , sum = 1.300000122948093e+01 , elapse = 0.027957
69 rational nume / deno addition
70 wer = 1 , n = 2 , sum = 1.500000000000000e+00 , elapse = 0.000000
71 wer = 2 , n = 4 , sum = 2.083333333333333e+00 , elapse = 0.000000
72 wer = 3 , n = 11 , sum = 3.019877344877345e+00 , elapse = 0.001030
73 wer = 4 , n = 31 , sum = 4.027245195436520e+00 , elapse = 0.001998
74 wer = 5 , n = 83 , sum = 5.002068272680166e+00 , elapse = 0.001998
75 wer = 6 , n = 227 , sum = 6.004366708345566e+00 , elapse = 0.003051
76 wer = 7 , n = 616 , sum = 7.001274097134161e+00 , elapse = 0.005050
77 wer = 8 , n = 1674 , sum = 8.000485571995780e+00 , elapse = 0.009068
78 wer = 9 , n = 4550 , sum = 9.000208062931140e+00 , elapse = 0.030012
79 wer = 10 , n = 12367 , sum = 1.000004300827581e+01 , elapse = 0.096833
80 wer = 11 , n = 33617 , sum = 1.100001770863643e+01 , elapse = 0.440332
81 wer = 12 , n = 91380 , sum = 1.200000305166563e+01 , elapse = 2.853218
82 wer = 13 , n = 248397 , sum = 1.300000122948078e+01 , elapse = 19.173152
83 rational simple addition
84 wer = 1 , n = 2 , sum = 1.500000000000000e+00 , elapse = 0.000000
85 wer = 2 , n = 4 , sum = 2.083333333333333e+00 , elapse = 0.000997
86 wer = 3 , n = 11 , sum = 3.019877344877345e+00 , elapse = 0.000997
87 wer = 4 , n = 31 , sum = 4.027245195436520e+00 , elapse = 0.001996
88 wer = 5 , n = 83 , sum = 5.002068272680166e+00 , elapse = 0.002991
89 wer = 6 , n = 227 , sum = 6.004366708345566e+00 , elapse = 0.003988
90 wer = 7 , n = 616 , sum = 7.001274097134161e+00 , elapse = 0.019946
91 wer = 8 , n = 1674 , sum = 8.000485571995780e+00 , elapse = 0.030916
92 wer = 9 , n = 4550 , sum = 9.000208062931140e+00 , elapse = 0.061500
93 wer = 10 , n = 12367 , sum = 1.000004300827581e+01 , elapse = 0.295848
94 wer = 11 , n = 33617 , sum = 1.100001770863643e+01 , elapse = 1.830510
95 wer = 12 , n = 91380 , sum = 1.200000305166563e+01 , elapse = 12.718921
96 wer = 13 , n = 248397 , sum = 1.300000122948078e+01 , elapse = 97.580847