s.AdditionRoundingError()));}誤差を計算に入れた足し算が実行されるようになります。いうクラスの単純なラッパです。フィールドでできあがっています。「指定された精度の範囲までは正確に実数を表現する」クラスです。変わった実装でもなかったので、詳細は省略。仮数部と指数部による表現。小さい値は正確に表現しきれないようですね。「計算式のツリー構造を作って、必要な時に必要な精度をもったEncapsulationをEvaluate()で計算する」という構成になっていることはわかりました。「必要な時」っていつでしょう。これには、3パターンあります。変換するとき大小比較するとき他の計算はすべて、計算式のツリー構造をひたすら積み上げていくだけです。値の表示は、ようは桁数を指定しての文字列への変換なので、これとdoubleへの変換の時は、指定された必要精度になるようにEvaluate()します。メソッドが肝心の処理を実行してます。現在の計算精度を表すグローバル変数です。設定するメソッドです。このように、必要精度はグローバルにはグローバル変数で引き回されてる実装です。精度で下から順に計算していくメソッドです。スタックオーバーフローしないように実際の再帰はスタック操作で頑張って書かれていますが、やることはそれだけなので詳細略。始めるので誤差が積もって本来必要な精度に足りなくなることもありますが、足りればその値を返します。(1);}・・・キャッチ。g_WorkingPrecisionを何倍かして、再計算。精度を上げる倍率は、現バージョンのソースコードでは2倍となっていました。これで末端精度を上げていけばそのうち最上位の精度も足りるようになります。低精度の桁を何回も計算し直すことになるので遅そうですけど、幅優先と反復深化の差みたいなもので、実際にはこっちの方が効率的だったりするのかな。大小比較は、RealLibでは「引き算して正か負かを判定」という実装になっています。つまるところ必要なのは、確実に正か負かわかる(=誤差範囲にゼロが含まれなくなる)まで精度を上げる、という処理です。r.IsPositive();}この処理は、MakeNonZero関数の担当。(1);}構造はMakeGoodEstimateとまったく同じですね。ゼロではなくなったかどうかを判定しています。あとは2倍ずつ精度をあげていくのみ。足し引き掛け割りは、概算値と最大誤差の間の計算によって見積もることができます。足し算は上で引用したように、誤作動しも足し算、掛け算はこんな感じ。r.MultiplicationRoundingError()));}三角関数や指数関数、πなどの値は、テイラー展開やニュートン法などを使って、必要な精度に収束するまで近似を繰り返します。計算して(πを直接算出するよりも楽)、逆数を求めて返す、という感じになってます。13)という収束列だそうな。この級数は1ステップで精度が4倍に上がることが知られているらしく、その結果を使って必要な回数でループを止めます。}}他の無限級数で計算される関数も止め方はだいたい同じようでした。ようするに、連続である、というのがこの手の実数計算の基本的な原理のひとつなみたいですね。ような不連続関数は提供されていないし、比較演算はちょうど等しいときにうまく動かなかったりする。実装は、値を計算式の形で覚えておいて、精度が必要になったら、精度を上げて下から再計算、というものでした。逆向きに、値を遅延評価のリストとして計算しておいて、上の方で精度が必要になると遅延された評価が実行されて、下の方のリストの遅延評価をさらに進める・・・といった実装もあるようです。究極的にはほぼ同じことが起きる形になっていると思いますが、実装の雰囲気はかなり違ってきそうなので、そういうののソースも機会があれば読んでみたいところです。