2025年12月22日月曜日

MELで四捨五入

 数値を表示しようとしたとき、少数をある桁数で区切りたいと思う事があります。いわゆるROUND関数というヤツです。

 MELのコマンドヘルプで検索してみても見つかりません。
 Program Filesの binフォルダで Grepを掛けてみると幾つかヒットしますが、どれも一の位で切り上げるのか切り捨てるかの計算をしているようです。
 必要なのは少数の何桁まで表示するのかを指定したいコマンドなのですが、どうやら公式には存在しないようです。

 そこで、MELから Pythonコマンドを読んでみようとすると、mayaでも導入された python3では round関数の仕様が変わり、四捨五入ではなく銀行丸めと言う方法で計算するように変更されたようです。

python3の銀行丸め

  特殊なルールがあり、想定とブレるため使い辛い感じがします。
 decimalモジュールを読み込むのも手ですが、そこまでしたくはない という。

 もう自作するしかない感じですね。

proc string _round(
     float $value                       ///< 値
    ,  int $digit )                     ///< 桁数
/******************************************************************************
    指定の桁数で四捨五入する。
 ******************************************************************************/
{
    float $mlt = pow( 10, $digit );
    float $sub = pow( 10,-$digit );
    float $pls =( 0 < $value ) ? 0.5: -0.5;
    float $val =((int)(($value * $mlt) + $pls) * $sub);
    
    return (string)$val;
    
} 

 処理内容としては、10の桁数乗で掛けて0.5か-0.5を足したところに10の桁数乗で割っている感じです。
 文字列として返しているのは、floatで返してしまうとe表記になってしまう事があるので、それを回避しています。
 あくまで表示に特化した処理にしています。

 これを global procにしてしまうと、今使用している幾つかの roundプロシージャを上書きしてしまいかねないので要注意です。
 まぁ、アンダーバーを付けているので、そうそうオーバーライドすることは無いと思いますが・・・。

 こういう事もあるから公式でroundコマンドを実装できないのかなぁとも思いました。

 EXCELなどでROUND系の関数を見てみると、ROUNDUPとROUNDDOWNに分かれているようです。こういった感じなら追加できそうな気もしますが・・・。



0 件のコメント:

コメントを投稿