1. HOME
  2. KAYO NEWS
  3. 不定期配信 マウスちゃんとメモリ主任のIT1年生44

KAYO NEWS

華陽ニュース

不定期配信 マウスちゃんとメモリ主任のIT1年生44

情報の重要性が増す昨今、弊社では情報セキュリティについて、その意義や情報を共有する取り組みを続けています。
担当チームが社内向けにまとめた資料などを基に、軽い読み物を不定期でお届けできればと思いますので、ご笑覧頂ければ幸いでございます。

 「あれ?」
 ある日の終業後。退社の用意をしていたマウスちゃん、イーさんの小さな声に動作を止めます。
 「どうしたんですか、イーさん?」
 「表計算ソフトの演算結果がおかしくて・・・C列が1以上ならD列は1、未満なら0っていう関数を設定してあるんだけど、この行のC列が1なのにD列が0になっちゃうんだ。」
 「本当ですね・・・でもA列からD列までは正しい数字や計算式が入ってますよね・・・」
 「だよね?」
 「・・・ひょっとしてウイルス?」
 「え?!」

 「大丈夫ですよ。これはウイルスではなく、『誤差』です。」
 慌ててやってきた2人を落ち着かせるように、メモリ主任が穏やかに応えます。
 「誤差、ですか?でも明らかにこれは1になるはずの計算式ですよね・・・」
 「誤差、というか、表計算ソフトの限界、といいますか。お二人は表計算ソフトがどうやって計算をしているかご存じですか?」
 「え?」
 「例えば『3+4』の場合は?」
 「えっと・・・」
 「基本的にコンピューターは『1』か『0』かで全てを処理します。そう考えると?」
 「あ、なるほど、2進数で考えるんですね。」
 「そういうことか。10進数の『3』は2進数の『11』、『4』は『100』だから」
 「『11』+『100』で『111』、これを10進数に直すと2の2乗+2の1乗+2の0乗=4+2+1で『7』が出てくる!」
 「そうですね。では『0.5+0.25』は?」
 「えっとこれも2進数で考えるとすると、0.5は2のマイナス1乗で0.25は2のマイナス2乗だから、2進数的には『0.1+0.01』の計算ってことですよね?出てくる『0.11』を同じように10進数に戻して結果は『0.75』です。」
 「その通りです。ちなみに、10進数の数の小数点以下を2進数に直す場合、2をかけて整数部をとる、という方法があります。例えば10進数の『0.375』を2進数にする場合

0.375X2=0.75・・・計算結果も1未満だから小数点第1位は『0』
0.75X2=1.5・・・整数部が『1』だから小数点第2位は『1』、今度は小数点部分の『0.5』だけを残して
0.5X2=1・・・小数点第3位は『1』、小数点部分がなくなったのでここで終了

という方法で、2進数では『0.011』になる、という結果を導く方法です。」
 「確かに、0.375を0.5で割って商が0だから第1位は0で・・・てやるより早そうですね。」
 「そうですね。では、それを踏まえて『0.5+0.45』は?」
 「えっと、0.5は『0.1』だから、さっき教えて頂いた方法で0.45を2進数に変換すると、

0.45X2=0.9・・・小数点第1位は『0』
0.9X2=1.8・・・第2位は『1』
0.8X2=1.6・・・第3位は『1』
0.6X2=1.2・・・第4位は『1』
0.2X2=0.4・・・第5位は『0』
0.4X2=0.8・・・第6位は『0』
0.8X2=1.6・・・

 あれ?」
 「戻ってしまいましたね。こういう風に延々と小数が続くものを『無限小数』、この場合は同じ数字のセットを繰り返すことになりますので『循環小数』ともいいます。中学生のころにならったかもしれませんが。」
 「・・・」 
 

 「2進数の1桁の『0』あるいは『1』がコンピューターには1ビットに当たります。説明のために単純化すると、10進数の『3』は2進数では『11』ですから、8ビットで数を表すコンピューターは10進数の『3』を『00000011』と表現するわけです。」
 「少数の場合はどうするんですか?」
 「いくつかありますが、そのうちのひとつが、32ビットで小数を表現する方法です。32ビットのうち、1ビット目でその数が正か負かの符号を、次の8ビットで2を基数とする指数を、残りの23ビットでその数自体を表現する方法ですね。」
 「例えば2進数が『0.010101』なら『00010101』になるとか?」
 「違います。ですが、そこを詳しく説明すると長くなるのでまたの機会にしましょう。分かって頂きたいのは、32ビットにせよ、あるいは64ビットや128ビットにせよ、数を表すビットは定数が決まっていて有限だということです。」
 「なるほど。無限小数や循環小数を表そうとしても、ビットの方の数に限りがあるから無理ってことなんですね。」
 「その通りです。なので、コンピューターは決められたビットに収まりきらない部分を切り捨ててしまいます。切り捨てられるのはごく小さな数に該当する部分ですので、普通は誤差に気づくことはありませんが、イーさんが使っておられる表のように、厳密に規定数以上かそうでないかを判定させるとか、同じ数かどうかを判定させるような場合だと、そのわずかの誤差で意図しない判定になる場合があるのですよ。」
 「たまに、『0』であるはずのセルの計算結果が『1E-21』みたいな表記になることがあるんですけど、その場合も同じことを疑った方が良いということですね。」

 「イーさんのこの表のものは『演算誤差』や『丸め誤差』と呼ばれる現象ですが、演算結果が扱える範囲を超えてしまう『けたあふれ誤差』や、あまりにも小さい数が無視されてしまう『情報落ち』など、コンピューターにはさまざまに誤差が生じる場合があるので、注意が必要ですね。」
 「0.000000001みたいな小さな数字を扱う時は要注意、ということですね。」
 「小さい数だけ見ていればよいわけけではないのが悩みの種なのですが。例えば、イーさんのこの表の数値はとても単純な数字で、計算結果は一目瞭然で『1』ですよね。でも、これが『1』と一致するか、を計算式で判定させると一致しない、という答えを出しています。それが、例えば元のデータの整数部をこう変えてみると」
 「一致する、って判定しますね・・・訳が分からない・・・・・・・どういう対処をすれば良いですか?」
 「結果を丸める、判定に影響を与えない小さな補助数を加算する、小数の計算でずれが生じるので小数では計算させないような作りにする、計算のもとになるデータの正規化の段階での注意、などでしょうか。コンピューターとしては、訳はちゃんとあるのですよ。ただ、私たちの目にはそれが判定できないことがあるので、コンピューターが計算しやすい数字にしてあげるか、計算が間違っていても最終的な結果には影響を与えないような工夫をするか、などですね。」

 とりあえずこの表の場合は・・・と対処方法を教えてもらった二人。席に戻ったときには退社時刻を大幅に越してしまっています。
 「ごめんね、マウスさん。僕の資料なのに、遅くまで付き合ってもらって。」
 「いえいえ、そもそも『ウイルスかも』って言い出して驚かしたのは私ですし、表計算ソフトの結果は間違いないって思ってたので、違うこともあるって分かって良かった、とも思いますし。それに」
 マウスちゃん、時計を見上げて
 「この程度の時間オーバーなら『誤差』の範囲ですよね。」
ドヤ顔で笑うのに、感激したようにイーさんが言います。
 「マウスさん、何が飲みたい?お礼に何でもおごるよ。」
 「えー、じゃあ、期間限定バーガーとポテトとシェイクと・・・」
 「待って!外に行くとは言ってないよ!休憩室の自販機!」
 「いえいえ、それも『誤差』の範囲内ですよね。」
 にぎやかに軽口をたたきながら休憩室へと向かう、ある晩秋の出来事でした。