• Resolved kyosuketanaka

    (@kyosuketanaka)


    こんにちわ。
    早速ですが、表題の件でトピックを立てさせていただきました。

    本プラグインを使用し色々と設定を行っていたところ、INT関数について不明な動作がございました。
    自動項目の金額欄にて下記のような計算式を設定したところ、出力結果がおかしなことになりました。

    ■フォーム設定
    端数の処理方法 : 切り落とし
    端数処理のケタ : 3

    【1】INT(100*1.15) = 114.000
    【2】INT(100*1.25) = 125.000
    【3】100*1.15 = 115.000

    【1】の設定の場合において、正しくない結果となりました。
    1.15の部分を様々な数値で試したところ、数値により正しい結果が出たり出なかったりしました。

    また、INTをTRUNCに変更したところ、下記のような結果となりました。

    【4】TRUNC(100*1.15) = 114.990
    【5】INT(100*1.25) = 125.000

    こちらの現象についてですが、私の設定や関数の使用方法が間違っているのか、もしくはプラグインのバグなのか、ご教示いただけますと幸いです。

    何卒よろしくお願いいたします。

Viewing 4 replies - 1 through 4 (of 4 total)
  • Thread Starter kyosuketanaka

    (@kyosuketanaka)

    本件につきまして、追加のご連絡となります。
    動作を色々と試していたところ、INTやTRUNC関数に限らず、おかしな出力となっているようでした。

    自動項目で下記のような設定を行い、出力した結果を記載いたします。

    【自動項目1】
    [金額]
    INT(100 * 1.15)
    =114.000

    [数量]
    500

    [合計]
    57,000.000

    【自動項目2】
    [金額]
    100 * 1.15
    =115.000

    [数量]
    500

    [合計]
    57,499.999

    以上となります。
    この現象につきましてご確認いただけますと幸いです。
    よろしくお願いいたします。

    Plugin Author vividcolorsjp

    (@vividcolorsjp)

    @kyosuketanaka

    回答するのが難しくて遅くなりました。
    結論から言うと、今のところ仕様ということになります。議論の余地はあるかと思っています。

    ■AFormsにおける計算の方法について

    計算で誤差が生じる原因ですが、これは一般的な小数点演算ではよくあることです。
    Excelなんかも同じで、1.2 – 1.1が0.1ではなく0.99999999だったりします(9がいくつ続くかは環境によって違うはずです)。
    この演算方法はIEEE754という規格に基づくものですが、デファクトスタンダードになっていて、ブラウザ上であろうがサーバー上であろうが基本的にはこの演算方法で計算が行われます。

    それとはまた別の話で、金額の計算で誤差が生じては困るので、ECシステムやら会計システムでは別の方法で計算していることもあります。
    ただし、金額の計算では「べき乗」のような高度な計算は不要なので、そもそも使えない場合もあります。

    AFormsでは、数式を使った場合はIEEE754に従って計算が行われます。
    また、明細行の金額(単価×数量)の計算では、その計算をした後に端数処理(フォーム設定で設定できるもの)を行うことで、誤差を適宜補正できるようにしてあります。

    ユーザー視点の意見として、AFormsにおける計算で「べき乗」などの高度な計算ができる必要があるのか、そのために誤差が生じるのはどうなのか、というのはあるかなと思います。
    難しいところです。

    ■kyosuketanakaのケースで何が起こっているか(10月4日の書き込みについて)

    【自動項目1】では、”100 * 1.15″の結果が114.99999などになり、INT()で切り捨てられて単価が114.000になっています。

    【自動項目2】も、”100 * 1.15″の結果が114.99999などになり、そのため明細行の金額は114.999999×500≒57,499.99999が端数処理された57,499.999になっています。
    単価の表示が”115.000″になるのは、114.999999を表示のためにフォーマットした結果です。

    Thread Starter kyosuketanaka

    (@kyosuketanaka)

    大変丁寧にご回答いただきまして誠にありがとうございます。

    浮動小数点の計算上における端数処理での誤差ということですね。
    あまり小数点を扱うプログラムを扱ってこなかったため気づきませんでした。
    いわれてみれば納得です。

    適切にROUND関数で整えていく必要があるようですね。

    Plugin Author vividcolorsjp

    (@vividcolorsjp)

    @kyosuketanaka

    適切にROUND関数で整えていく必要があるようですね。

    そうですね。
    他には、あらかじめ100倍しておいて、すべて整数で計算するようにする方法もあります。

Viewing 4 replies - 1 through 4 (of 4 total)
  • You must be logged in to reply to this topic.