経緯
過去に色々
$a = $_GET['a'];
みたいなコードの是非を巡ってPHPと闘ってきましたが…
いずれにも以下のような欠点がありました。
-
filter_input
で一発処理出来るのは外部から受け取る値かつ文字列のみ - 上記に該当しないものには
isset
とis_string / filter_var
の処理がどこかで必要になってくる
PHP7からは…?
PHP7には**NULL合体演算子??
**が導入されており、任意の変数に対して
- 未定義でもNULLでもなければ左オペランドの値を採用
- 未定義またはNULLのとき右オペランドの値を採用
(内部でisset
相当のチェックを行っているのでエラーが発生しない)
という処理を記述することが出来ます。
文字列型のみ処理したい場合
filter_inputでの書き方
$a = filter_input(INPUT_GET, 'a'); // 未定義の場合は null, 配列の場合は false になる
if (is_string($a)) {
/* 正常系の処理 */
}
NULL合体演算子での書き方
$a = $_GET['a'] ?? null; // 未定義の場合は null になり, 配列の場合は配列のまま
if (is_string($a)) {
/* 正常系の処理 */
}
文字列型を強制する場合
filter_inputでの書き方
$a = (string)filter_input(INPUT_GET, 'a'); // 未定義や配列の場合は空文字列になる
NULL合体演算子での書き方
$a = (string)filter_var($_GET['a'] ?? ''); // 未定義や配列の場合は空文字列になる
考察
filter_input
と比較したときの長所
配列がネストしていても大丈夫。 これに尽きます。
$a[0] = (string)filter_var($_GET['a'][0] ?? '');
もうちょっと楽をしたければ、htmlspecialchars
に対してh
というラッパー関数を割り当てる感覚で
$varは値渡し
function s($var) {
return (string)filter_var($var);
}
という関数を作っておくと
$a = s($_GET['a'] ?? '');
と書けます。文句無しですね。
実はPHP5でも…
これは賛否両論あると思いますが、未定義の要素が勝手にNULL初期化されても問題無いのであれば
$varは参照渡し
function s(&$var) {
return (string)filter_var($var);
}
という関数を作っておくと
$a = s($_GET['a']);
で済みます。大事なことなので二度言いますが、未定義でも勝手に
$_GET['a'] = null;
という処理が走るのであまりおすすめは出来ません。