本ページは公開が終了した情報の複製であり、掲載時点での情報です。本ページに記載されている内容について各所に問い合わせることはご遠慮下さい。
サポート技術情報

[XL] 浮動小数点の計算誤差と IEEE フォーマット

文書番号: 402554

最終更新日: 2002/05/02


この資料は以下の製品について記述したものです。


この記事は、以前は次の ID で公開されていました: JP402554

概要

本文書では、Excel 5.0 を始めとする多くのアプリケーションで問題となる数値の
「誤差」について、若干技術的に解説をしています。

コンピュータの数値表現

私達はほとんどの場合 10 進数で計算を行います。しかし、コンピュータにとって
は 2 進数の方が便利です。コンピュータは電気的に動作しており、その電気のオ
ンかオフの状態を「 1 」と「 0 」として捉えるのが最も簡単だからです。この最小単 位を「ビット」と呼びます。1 ビットでは 2 種類、4 ビットでは 16 種類の表現が
可能です。このビットを増やすことで、扱える表現数は増えることになります。
コンピュータのメモリは無限ではありません。円周率や循環小数などを完全に表す
ことは不可能です。そこである一定の桁でまるめてしまうことが必要になりま
す。メモリは (ハードディスクなどに比べると) 比較的高価なデバイスですの
で、できるだけ少ないメモリでできるだけ大きな数字や小さな数字を表現する
という相矛盾する要求を満たさなければなりません。また、1 つの数値を表す
のに少ないメモリであれば計算速度も向上します。これらのことを踏まえて、
いくつもの数値データの格納形式が発明されました。当初コンピュータは科学
技術計算に用いられることを目的として作られましたので、精度よりも、計算
速度や扱える数値範囲の大きさの方が優先されていました。その中で生まれたのが
今回ここで紹介する IEEE の浮動小数点フォーマットです。

Intel 系 CPU を使ったパーソナル コンピュータ

Intel 系の CPU (80386、80486、Pentium など) および数値演算プロセッサは IEEE
(後述) で定められた数値のフォーマットに則ってデザインされており、このフォー
マットでの演算コマンドをハードウェア レベルでサポートしています。このためこ
の CPU を使ったオペレーティング システムおよびその上で動作するアプリケー
ションは、自動的にこのフォーマットに従ったものになります。これ以外のフォ
ーマットを使用したときには、ソフトウェアで演算の総てを行わなければなりま
せんので、速度的には大きなペナルティとなります。Intel 系 CPU でサポート
されている数値フォーマットおよびその派生は以下の通りです。
    整数         (Integer)
    長整数       (Long Integer)
    単精度実数   (Single)
    倍精度実数   (Double)
    長倍精度実数 (Long Double)
これらの数値フォーマットを使う限り、ハードウェアの助けを借りることができます。 ただし、Microsoft(R) Windows(R) (以下 Windows) の環境で実数については浮動小
数点演算プロセッサ (ユニット) が無いときにはソフトウェアでエミュレートしま
す。例えば、i80386 CPU は標準でこのユニットを持っていません。別途専用の
i80387 コプロセッサが用意されており、これと組み合わせることで実数の演算を
ハードウェアで行うことができます。これに対し、i80486DX や Pentium プロセッ
サなどは、その内部に浮動小数点演算ユニットを内蔵しています。

IEEE の浮動小数点フォーマット

IEEE 形式は、米国電気電子技術者協会 (Institute of Electrical and Electronics Engineers) により、おもにパーソナル コンピュータで使用される浮動小数点の形
式を統一するために定められました。808x6 を含む 16/32 ビット CPU に対応する
コンパイラなどがこの規格に統一されており、80x87 などの数値演算コ・プロセッ
サとも相性のよい標準的なデータ形式です。
                   単精度  倍精度
    指数部ビット数    8      11
    符号ビット数      1       1
    仮数部ビット数   23      52
    有効桁数          7      15
これに対し、速度や扱える数値の範囲より、精度を重要視するフォーマットも存在し ます。オフィスコンピュータの世界でよく用いられるのが 4 ビットで 1 桁の数値を 表現する形式や小数点以下の桁を固定する、固定小数点形式で、これらは扱える数値 の範囲は狭くなりますが、正確に数値を表現できます (メーカーによってフォーマッ トの細部は異なります) 。

浮動小数点形式への格納による誤差

浮動小数点数は小数点の位置を一定とせず、有効数字を表現する仮数部と小数点の位置 を示す指数部を用いて表します。指数部は数値の大きさの範囲を定める部分で、2 の べき乗を 2 進数で表現します。負の値の指数は、相対的なバイアス値を加算すること により表現します。仮数部は数値の精度を定める部分で、この値に指数部の計算を
施して元の値を表現します。この仮数部の大きさが 4 バイト長の浮動小数点数を
「単精度」、8 バイト長の浮動小数点数を「倍精度」といいます。まず、この段階
で小数点以下の数値は精度が落ちます。多くの小数点以下の数値は上記の方法では
完全な精度での 2 進数化ができません。
また浮動小数点演算において、許容範囲を越える負の指数が生じたときは桁落ち
(アンダーフロー) が発生します。また、仮数部の有効桁数を越えた数値を表現
するとき、超越分をなくさないため値を左右にシフトし、それに伴って指数部の
増減を行います。この操作を正規化といいますが、正規化が行われると誤差が生じ
精度が落ちます。このため実数の場合には循環小数となって完全に表現しきれない
ことがあります。この誤差は計算上問題となりますので、保証できる精度の範囲を
もって、「有効桁数」という言葉で表します。
Excel 5.0 の場合には 15 桁が有効桁数です。つまり 15 桁以上のところには
誤差が含まれている可能性があるということです。しかし、この誤差を含んだ
数値を演算した結果、14 桁以内に誤差が現れることもあります。

Excel 5.0 上での数値データの扱い

Excel 5.0 では、数値は 2 種類のフォーマットで扱われます。1 つは整数で、もう
1 つは実数です。整数は -32,768 から +32,767 までの小数点を含まない数値で、
それ以外の数値はすべて IEEE 形式の倍精度実数扱いです。いったんセルに入力
された整数の範囲を越える数値は IEEE 形式の浮動小数点フォーマットに変換さ
れてメモリに格納されます。
そして瞬時に、指定された書式で変換して画面に表示します。したがいまして、入力 された数値がそのままセルに表示されているとは言っても、有効桁数の範囲外の部分 もしくは表示形式によって表現される範囲外の部分に誤差を含んでいる可能性がある ことになります。
ここで表示される桁より下の桁をどう処理するかが問題となります。この処理を
「まるめ」と呼んでいますが、これにも IEEE で幾つかのルールが決められてい
ます。パーソナル コンピュータの世界では、「最近偶数値 の 2 の数値まるめ」
という方法を取っています。この処理は Excel 5.0 というよりもハードウェアも
しくは Windows が行っています。さらに詳しいことがお知りになりたいときには、
IEEE の規格書もしくは Intel 社の 80x87 の仕様書を参照ください。

Excel 5.0 上での計算方法

既定値では、Excel 5.0 は表示されている値ではなく、セルに保管されている値で
行っています。すなわち実数では演算誤差を含んでいる可能性があります。また、
整数同士の演算で、結果も整数の範囲で収まるものは誤差は伴いません。しかし、
それ以外の場合には一端実数にキャスト (型変換) された後、演算が行われます。こ のときにも演算誤差を含むことがあります。ほとんどの場合、これらの誤差は有効
桁数外で発生しますので問題になることは、そう多くはありません。ただし、有効
桁数の範囲内では同じ数値であっても、範囲外の値が異なっているときには IF 関
数などによる比較で問題となるケースも発生します。これらのときには ROUND 系の
関数でまるめを行ったあとに比較をすることで回避できます。
表示されている値 (桁数) で計算させたいときには、[ツール] - [オプション] コ
マンドの [計算方法] パネルで、[表示桁数で計算] チェックボックスをオンに
することで行えます。この設定は、[オプション] コマンドで設定することから
も判るとおり、Excel 5.0 全体に影響を与えます。また表示形式によって表示桁
数を指定しているときには、正確さも失われる可能性がありますので、設定にあ
たっては十分な注意が必要です。

参考: VBA での通貨型

Microsoft(R) Visual Basic(R)Programming System Applications Edition 内部に
は通貨型というデータ型を持っています。これは浮動小数点形式のフォーマットで
は無く、固定小数点形式の独自のフォーマットです。浮動小数点と異なり、小数点
の位置を固定することで扱える数値の範囲は狭くなりますが、誤差を含ませないと
いう利点があります。このため、金額を扱う計算のために使われるデータ型として
定義されています。
この型の有効桁範囲は整数部 15 桁+小数点以下 4 桁です。これは Microsoft(R)
Visual Basic(R) for Windows(R) / MS-DOS(R)、Microsoft(R) BASIC Version 7.0
でサポートされているものと同じです。

サンプル

  Sub Sample()
      '計算に使用する変数を通貨型で定義します
      Dim Kingaku As Currency, Zeiritsu As Currency
      '計算に使用する値を変数に代入します
      Kingaku = 1995
      Zeiritsu = 1.03
      '計算結果を整数にして値を求めます
      Kingaku = Int(Kingaku * Zeiritsu)
      MsgBox Kingaku
  End Sub
通貨型のデータを定義して計算に使用する場合は、その計算式で使用するデータのすべ てを通貨型に定義した変数に代入して計算を行なうようにしてください。
計算結果を整数化する必要がある場合には、目的の処理に応じて Int、Fix などの
VBA 関数を使用するか、Round、RoundDown、RoundUp などのワークシート関数を使用 して調整するようにしてください (サンプルでは、Int 関数を用いて計算結果を整数 化しています)。
各関数の機能および詳細は、オンライン ヘルプを参照してください。

Keywords: KBINFO KB402554
Technology: kbExcel500 kbExcelSearch kbExcelWinSearch

inserted by FC2 system