正木です。

|[ruby-math:00811] Re: Rational#to_f
|From: keiju / rational.com (石塚圭樹)
|
|以下のようなもので計算するのはいかがでしょう? 
|
|  BASE = 2.0
|  def Rational.precsize_of_float
|    i = 0
|    diff = 1.0
|    while 1.0 != 1.0 + diff
|      i += 1
|      diff /= BASE
|    end
|    i - 1
|  end
|  FLOAT_PRECSIZE = Rational::precsize_of_float


どんな Float の実装があるか分からないのでなんとも言えませんが、
常識的にはこれで良いはずだと思います。

私も

class Float
  def Float.precsize_of_float
    i = 0
    i += 1  while 1 + Math.ldexp(1,-i) != 1
    i - 1
  end
  PRECSIZE = precsize_of_float

  def to_Rational
    m=PRECSIZE + 1
    a,e=Math.frexp(self)
    (2**m*a).to_i/2**(m-e)
  end

  def to_rational
    m=PRECSIZE + 1
    e=Math.frexp(self)[1]
    error=1/2**(m-e)
    to_Rational.to_Real.approx(error)
  end
end

class Bignum
  def to_f
    m=Float::PRECSIZE
    n=abs.log2floor - m
    if n < 0
      Math.ldexp(self,0)
    else
      Math.ldexp((self*2+2**n) >> n+1,n)
    end
  end
end

class Rational
  def to_f
    m = Float::PRECSIZE
    e = m - abs.log2floor
    Math.ldexp((self*2**e).round,-e)
  end
=begin
  def to_f
    m=Float::PRECSIZE + 1
    e = m - abs.log2floor
    Math.ldexp((self*2**e).floor.to_f,-e)
  end
=end
end

という形で取り入れることにします。


|ところで, 正木さんのRealってどこかアクセスできるようなところに置いてあ
|るんですか? テストに使おうかと思ったのですが, 見当たらなかったもので...

以前

|[ruby-math:00754] [Q]Gamma & Zeta functions

|Real Class の修正が重なったのと、自分で使っていて、ある程度実用的になった
|と思うので、ここで公開して、皆さんの御批判及び advice を受けたいと思ってい
|るんですが、興味を持つ人がいなさそうなのと、あまり長い script をここに流す
|のも迷惑かも知れないと思って躊躇しています。
|坂野さんには直接 mail でお送りします。
|もし他にも興味のある人がいれば mail を下さい。
|

と書いたのですが、興味をもってくれる人が現れなかったのでそのままになって
います。

石塚さんには 直接お送りします。tar.gz で圧縮して 28 K  位です。