SOFTELメモ Developer's blog

会社概要 ブログ 調査依頼 採用情報 ...
技術者募集中

【php】やってしまうと見つけにくい不具合

問題

↓ これは普通の結果ですが…

$ php -r 'var_dump(1  >  2);'
bool(false)

↓ これはどうしたことでしょう?

$ php -r 'var_dump(1  > 2);'
bool(true)

bug


答え

問題のスクリプトは、以下と似たような事態。2の前に全角スペースが入っている。

$ php -r 'var_dump(1 > ■2);'
bool(true)

$ php -r 'var_dump(1 > aa2);'
bool(true)

$ php -r 'var_dump(1 > 全角スペース2);'
bool(true)

以下の3点から、結果としてそうなる。


いろいろな例

「 2(全角スペースと2)」が未定義の定数として評価され、文字列” 2″となり、数字との比較で数字に変換されて、0となるため、「1 >  2」→ 「1 > 0」 → true となる。

うっかり変なところに全角スペースを入れてしまうと、見えないし、構文エラーにもならなくて(Noticeなら発生するが)、発見しづらい。

$ php -r 'var_dump(1 >  2);'
bool(true)

「 2(全角スペースと2)」で定数を定義できる。使用もできる。

# php -r 'define(' 2', 5); var_dump(1 >  2);'
bool(false)

ドル記号と変数名の間に全角スペースがあっても、構文は間違っていないので動く。さすがにこれは見て気づくと思うけど。

$ php -r '$a = 2; var_dump(1 > $ a);'
bool(true)

でもやっぱり、こういうことをしてしまうと見つけにくい($a代入時の2の前に全角スペース)。

$ php -r '$a =  2; var_dump(1 > $a);'
bool(true)

おばけのような全角スペースの話でした。

phpでは「全角の文字でも定数に使えるよ! & 未定義の定数は文字列扱いされるから気をつけてね!」ということで。

参考

【php】変数名に日本語を使ってもよい?

関連するメモ

コメント