PHP の strpos の戻り値判定は注意しよう!

任意の文字列の中に特定の文字列が存在しているか否かをチェックするときに、strposは便利な関数です。

任意の文字列中に特定の文字列があれば見つかった位置(ポジション)を返却してくれます。
見つからなかったときは false を返してくれます。
例えば、

<?php
    $org = "abcde"; 
    $reg = "bc"; 

    if (false != strpos($org, $reg)) {
        echo "Found!";
    } else {
        echo "Not Found!";  
    }
?>

のようなソースを実行したら、Found! が正しく返却されます。
ただ、false の != ってなんかちょっと気持ち悪いですよね。
なので、以下のように書き換えてしまいがちなんです。

<?php
    $org = "abcde"; 
    $reg = "bc"; 

    if (true == strpos($org, $reg)) {
        echo "Found!";
    } else {
        echo "Not Found!";  
    }
?>

でもこれは間違いです。
いや、動かしたらちゃんとFoundが返ってきたよ?と思うかもしれないですが「間違い」です。

なぜこのコードがうまくいったかというと、戻ってきたポジションの値が正の値だったため、trueとして有効になっただけなのです。
以下のコードに変えてみましょう。

<?php
    $org = "abcde"; 
    $reg = "ab"; 

    if (true == strpos($org, $reg)) {
        echo "Found!";
    } else {
        echo "Not Found!";  
    }
?>

ね、Not Foundになったでしょ。
posironに「0」が設定されて返却されたからです。phpの世界では0はfalse扱いなので、ポジション0は勝手にfalseにされてしまうんですね。

なのでそういう間違いをしないように、falseでなければ成功、としないといけないのです。
ではfalseでなければ成功として、もう一度確認しましょう。

<?php
$org = "abcde"; 
$reg = "ab"; 

if (false != strpos($org, $reg)) {
    echo "Found!";
} else {
    echo "Not Found!";  
}
?>

???あれれ、Not Foundが返ってきました。

そうなんです。 != ではだめなんです。 !== じゃないとダメなんです。
だって、0 がfalseになっちゃうわけですから。
ので、0 ではなく false かどうかを正確に判断しないといけません。

<?php
$org = "abcde"; 
$reg = "ab"; 

if (false !== strpos($org, $reg)) {
    echo "Found!";
} else {
    echo "Not Found!";  
}
?>

これでやっとうまくいきました!!

と思っていませんか?
では次を実施してみましょう。

<?php
$org = "abcde"; 
$reg = ""; 

if (false !== strpos($org, $reg)) {
    echo "Found!";
} else {
    echo "Not Found!";  
}
?>

おやおや、空文字なのに見つかったよ!となってしまいます。 strpos、空文字だと0が返ってくるんですね。困ったもんです。

そのため、以下のようにしないとうまくいきません。

<?php
$org = "abcde"; 
$reg = ""; 

if (strlen($reg) != 0 && false !== strpos($org, $reg)) {
    echo "Found!";
} else {
    echo "Not Found!";  
}
?>

たかが文字列検索ですが結構面倒でしたね。

以上!