LotusScript で実数を整数に変換する関数として Int と CInt 関数の 2 種類があります。PC が一般的になり始めたころに BASIC 言語を使用していた私には Int の方がなじみがあります。その経験から CInt も同じだろうと無頓着に使用してきましたが、微妙に差があったのでまとめておきます。
丸め方の違い
デザイナーヘルプによると次のように説明されています。
| Int | 引数に指定した数値に等しいか、それよりも小さい整数値のうち、指定した数値に最も近い値を返します。 |
| CInt | 値を Integer データ型に変換して返します。 最も近い整数に丸め、Integer 型の値として返します。 |
ニュアンスから関数の立ち位置が見えてきますね。Int は整数値に変換することを主題にしてています。CInt は型変換が主題で、その副次的機能として丸め処理が発生しているようです。
そして、小数値の処理である丸め方の表現に違いがあることがわかります。
丸め方の動作検証
それでは実際に処理の違いを確認しましょう。簡単なエージェントを作成し、Int と CInt の差を確認します。
|
Option Declare Sub Initialize xTest 1.5 End Sub Function xTest(vdVal As Double) MsgBox "Int(" & CStr(vdVal) & ") = " & CStr(Int(vdVal)) MsgBox "CInt(" & CStr(vdVal) & ") = " & CStr(CInt(vdVal)) End Function |
引数を変えながら動作検証した結果は次の通りでした。
| 1.1 | 1.5 | 1.9 | 2.1 | 2.5 | 2.9 | |
| Int | 1 | 1 | 1 | 2 | 2 | 2 |
| CInt | 1 | 2 | 2 | 2 | 2 | 3 |
Int は切り捨て処理であることが確認できます。しかし、CInt では 0.5 の処理が単純な四捨五入とは違います。この部分の動作を詳しく確認します。
| 1.49 | 1.50 | 1.51 | 2.49 | 2.50 | 2.51 | |
| Int | 1 | 1 | 1 | 2 | 2 | 2 |
| CInt | 1 | 2 | 2 | 2 | 2 | 3 |
プログラミングや統計の世界では、5 ちょうどの扱いを「常に切り上げない」といった仕様が使われることがあり、統計的に偏りが出にくいことを目的としています。
CInt はこの仕様を採用しており、ヘルプでは ”四捨五入” と表現せず、”最も近い整数に丸める” という表現になっているということですね。
負の数の対応
続いては、負の数の処理に関して確認します。
CInt の動作はわかりやすく、単に符号が付いただけの動作になります。
ところが、Int の場合は、絶対値が変化しています。これは、指定した値よりも ”小さい” 最も近い整数となるためです。
| -1.49 | -1.50 | -1.51 | -2.49 | -2.50 | -2.51 | |
| Int | -2 | -2 | -2 | -3 | -3 | -3 |
| CInt | -1 | -2 | -2 | -2 | -2 | -3 |
負の数はビジネスでは使用頻度が低いかもしれません。ただ、頻度が低いと間違い(確認漏れ)が発生しやすいので注意しましょう。
イレギュラーの対応
最後に、これら関数に対してイレギュラーな値を与えた場合の動作について整理します。
| テストデータ | 値 | Int | CInt |
| Integer の範囲を超える数値 | 77777.7 | 77777 | エラー |
| 数値に変換できる文字列 | "2.50" | 2 | 2 |
| 数値に変換できない文字列 | "14.5 FP1" | エラー | エラー |
| 日付/時刻 | Now | 2026/1/18 | エラー |
| Empty な Variant 型変数 | 0 | 0 | |
| 配列 | エラー | エラー | |
まず、この結果より Int 関数は名称から Integer 型と思いがちですが、Integer 型を超えた値の処理が可能です。そのおかげで日付/時刻データから時刻部分(小数値)を削除する演算としても使用可能です。
式言語の @TextToNumber で文字列を数値に変換する場合、変換できる範囲で実行する機能があります。例えば "14.5 FP1" は、14.5 に変換してくれるのですが、LotusScript では単純にエラーとなります。
Variant 型変数を引数にする場合には、Empty(変数の宣言だけして値を代入し忘れた状態)は 0 となり、配列やオブジェクトが入っている場合にはエラーとなります。
このような、イレギュラー処理が発生すること自体あまり良いコーディングとは言えないと思います。必要な場合はコメントに記すなど、後から見てわかるようにしておきましょう。
0 件のコメント:
コメントを投稿