Posted on

PHPの empty, isset, is_null の違いをしっかり理解する

PHPの isset、empty、is_null をしっかり理解して使おうと思い整理してみました。既にこのような記事「PHP isset, empty, is_null の違い早見表」もあるのでここではこれより少し踏み込んだところまで書いてみます。

empty, isset, is_nullの違い早見表

if ($var) empty isset is_null
$var = 1 true false true false
$var = array(1) true false true false
$var = “” false true true false
$var = “0” false true true false
$var = 0 false true true false
$var = array() false true true false
$var = false false true true false
$var = NULL; false true false true
$var false true false true

まず表ですが、順番を理解しやすい形に変えてみました。下記のように赤と青のグループで分けて考えておくと理解しやすいです。これをみると「if ($var)empty」、「issetis_null」が対になっているのがわかります。

感覚的には、if ($var)は値がありそうだなと思うものがtrueになり、emptyも値がなさそうだな思うものがtrueになる感じがします。issetは、何かしら値がセットされてばtrue(つまり値がfalseでも結果はtrue)、is_nullは値がnullであればtrueということになります。
実際の挙動の動作確認についてはPHPUnitを使ってテストしたものをGitHubにあげているので合わせて確認してみてください。https://github.com/taisa831/AimaiPHP

empty, isset, is_null の Notice や Error 出力早見表

次に、PHPのerror_reportingE_ALLにした場合に、indexのない配列にアクセスした場合やオブジェクトが空の変数や関数にアクセスした場合の挙動をまとめてみました。

if ($var) empty isset is_null
$var = [];
$var[0];
Undefined offset: 0 true false Undefined offset: 0
$var = [];
$var[‘hoge’]
Undefined index: hoge true false Undefined index: hoge
$var = null;
$var[‘hoge’]
null true false null
$var = (object)[];
$var->var;
Undefined property: stdClass::$func true false Undefined property: stdClass::$func
$var = null;
$var->var;
Trying to get property of non-object true false Trying to get property of non-object
$var = (object)[];
$var->func();
Error: Call to undefined method stdClass::func() Error: Call to undefined method stdClass::func() 実行不可 Error: Call to undefined method stdClass::func()
$var = null;
$var->func();
Error: Call to undefined method stdClass::func() Error: Call to undefined method stdClass::func() 実行不可 Error: Call to undefined method stdClass::func()

結果は、上の表のようになりました。オブジェクトに対して未定義の関数にアクセスした場合やnullから関数を呼ぼうとした場合全てにおいてErrorになります。それ以外では、emptyissetを使うとNoticeは出でませんが、if ($var)is_nullを使うとNoticeがでるという違いがあります。この辺の違いを理解しておくとPHPによる開発が進めやすくなると思います。スマホだと表が切れてしまうので画像も貼っておきます。