先日、入力チェックのプログラムを動かしているときのことです。
金額の大小チェックで妙なエラーが出るとの相談を受けました。
それは
・10000 < 10 はエラーになる
・10000 < 11 はエラーにならない(!)
ということだとか
た、確かに妙な現象だ。
しばらく考えるとあることが頭に浮かんだ。
もしかして文字列を数値型に変換していないんじゃないだろうか!
そして、String#compareToメソッドで大小比較していると・・・・
ソースを見ると・・・・
ずばり、そのとおりでした。
誰だよー、文字列のまま数字の大小チェックを行うロジックを書いた人はー
で、10000 < 10がエラーになり10000 < 11はエラーにならなかった理屈はJavaのString#CompareToメソッドに原因がある。
String#CompareToのソースは以下のとおり
String#CompareToのソースを見ると確かに
10000と10は10000が大きい
10000と11は11が大きい
となる。
現実世界の常識をそのままプログラミングに当てはめるとえらい目にあうなぁ、やっぱり
(後日談)
この件を会社の同僚に話すと
"それって、いわゆる辞書順ですよね"
という返事が返ってきた。
確かに、言われてみれば、辞書順で文字を比較するアルゴリズムだわ。
"tripleさんがそんなことを調べているなんて・・・
もしかして数字をcompareToで比較しているロジックが散見しているんですか?"
調べたのは暇つぶしみたいなものだが、ロジックが散見しているのは事実だよ。
いまから、その散見しているロジックを片っ端から直さないといけないけどね(泣)
金額の大小チェックで妙なエラーが出るとの相談を受けました。
それは
・10000 < 10 はエラーになる
・10000 < 11 はエラーにならない(!)
ということだとか
た、確かに妙な現象だ。
しばらく考えるとあることが頭に浮かんだ。
もしかして文字列を数値型に変換していないんじゃないだろうか!
そして、String#compareToメソッドで大小比較していると・・・・
ソースを見ると・・・・
ずばり、そのとおりでした。
誰だよー、文字列のまま数字の大小チェックを行うロジックを書いた人はー
で、10000 < 10がエラーになり10000 < 11はエラーにならなかった理屈はJavaのString#CompareToメソッドに原因がある。
String#CompareToのソースは以下のとおり
public int compareTo(String anotherString) { int len1 = count; int len2 = anotherString.count; int n = Math.min(len1, len2); char v1[] = value; char v2[] = anotherString.value; int i = offset; int j = anotherString.offset; if (i == j) { int k = i; int lim = n + i; while (k <lim) { char c1 = v1[k]; char c2 = v2[k]; if (c1 != c2) { return c1 - c2; } k++; } } else { while (n-- != 0) { char c1 = v1[i++]; char c2 = v2[j++]; if (c1 != c2) { return c1 - c2; } } } return len1 - len2; }
String#CompareToのソースを見ると確かに
10000と10は10000が大きい
10000と11は11が大きい
となる。
現実世界の常識をそのままプログラミングに当てはめるとえらい目にあうなぁ、やっぱり
(後日談)
この件を会社の同僚に話すと
"それって、いわゆる辞書順ですよね"
という返事が返ってきた。
確かに、言われてみれば、辞書順で文字を比較するアルゴリズムだわ。
"tripleさんがそんなことを調べているなんて・・・
もしかして数字をcompareToで比較しているロジックが散見しているんですか?"
調べたのは暇つぶしみたいなものだが、ロジックが散見しているのは事実だよ。
いまから、その散見しているロジックを片っ端から直さないといけないけどね(泣)
(関連文献)
![]() | Java本格入門 ~モダンスタイルによる基礎からオブジェクト指向・実用ライブラリまで |
クリエーター情報なし | |
技術評論社 | |
![]() | 改訂2版 パーフェクトJava |
クリエーター情報なし | |
技術評論社 |