gistでPHPのコードを読んでいたらこんな個所があった。
$array = array_filter(explode(' ', $value));
$value には aaa bbb ccc みたいなテキストが入ってる。なので explode をつかって $value をスペースごとに分割して配列にするところまでは分かる。(explode については PHP: explode - Manual を参照)
こんな感じのコードを書いて、
<?php $value = 'aaa bbb ccc'; $array = explode(' ', $value); var_dump($array);
実行するとこうなるんだよね。わかる。 aaa bbb ccc が explode で分割されて配列になった。
array(3) { [0]=> string(3) "aaa" [1]=> string(3) "bbb" [2]=> string(3) "ccc" }
でもこれにさらに array_filter かけても、
<?php $value = 'aaa bbb ccc'; $array = array_filter(explode(' ', $value)); var_dump($array);
実行結果はまったく同じ…んんん? array_filter なにしてるんだ…?( array_filter についてはこちら PHP: array_filter - Manual を参照)
$ php test.php array(3) { [0]=> string(3) "aaa" [1]=> string(3) "bbb" [2]=> string(3) "ccc" }
array_filter って 第2引数に「奇数だったらtrueを返すメソッド」みたいなのを指定して、配列の中から奇数の要素だけをフィルタリングする 的なメソッドだと思ってたので、そもそも第2引数が指定されてないと何してるの…?と。
うーんうーんと考えた結果、恐らく次の2つのケースのときに array_filter が役に立つから使ってるんじゃないかな?と推察したので書いておく。
ケース1. $value が空文字だったときに empty の結果が変わる
次のように $value が空文字だった場合、
<?php $value = ''; $array = explode(' ', $value); var_dump($array); var_dump(empty($array)); $array = array_filter(explode(' ', $value)); var_dump($array); var_dump(empty($array));
explode だけだと配列に「値が空の要素」が1件入るけど、 array_filter を組み合わせれば要素は0件になる。
array(1) { [0]=> string(0) "" } bool(false) array(0) { } bool(true)
こういうケースなら empty で空かどうかチェックしたときの結果が true と false で分かれるので、 array_filter がいる意味わかるー。( empty についてはこちら PHP: empty - Manual を参照)
ケース2. $value にスペースが沢山あったときに詰められる
あとは aaa bbb ccc みたいに $value にスペースがたくさんあったとき!
こういうときも explode だけだと要素数が7つになっちゃうけど、array_filter を通せばフィルタリングされて値のある3つだけになる。
<?php $value = ' aaa bbb ccc'; $array = explode(' ', $value); var_dump($array); var_dump(count($array)); $array = array_filter(explode(' ', $value)); var_dump($array); var_dump(count($array));
array(7) { [0]=> string(0) "" [1]=> string(3) "aaa" [2]=> string(0) "" [3]=> string(3) "bbb" [4]=> string(0) "" [5]=> string(0) "" [6]=> string(3) "ccc" } int(7) array(3) { [1]=> string(3) "aaa" [3]=> string(3) "bbb" [6]=> string(3) "ccc" } int(3)
こういうケースでも array_filter は有用そう!
ただし false や null があるときには要注意
explode で配列にしたときは、要素はすべて「文字列」として値に入るので、例えば -1 false null を渡した際に、
<?php $value = '-1 false null'; $array = explode(' ', $value); var_dump($array); $array = array_filter(explode(' ', $value)); var_dump($array);
こんな感じで array_filter を通しても全く問題ないのですが、
array(3) { [0]=> string(2) "-1" [1]=> string(5) "false" [2]=> string(4) "null" } array(3) { [0]=> string(2) "-1" [1]=> string(5) "false" [2]=> string(4) "null" }
配列に null やbooleanの false が入る場合は注意が必要そう。
<?php $value = [ -1, false, null ]; var_dump($value); $array = array_filter($value); var_dump($array);
実行してみると、こんな感じでさらっと false や null の要素がフィルタリングされて消えたー。
array(3) { [0]=> int(-1) [1]=> bool(false) [2]=> NULL } array(1) { [0]=> int(-1) }
-1 みたいなの負の数は消えないんだね。なるほど。
こういう「人が書いたコードの意図や、どんなケースを想定しているのかを考える」のは楽しいなー。
なお上記は CentOS 6.10 の PHP 5.6.40 のCLI環境で確認しました。