#php
В выражении if ($next['referer'] ?? null) { }
Ответы
Ответ 1
Это короткая форма (синтаксический сахар) тернарного оператора с isset() $referer = isset($next['referer']) ? $next['referer'] : '' который, в свою очередь, является короткой формой условного оператора if (isset($next['referer'])) { $referer = $next['referer']; } else { $referer = null; } Называется null coalescing operator, или в переводе, оператор объединения с null. Название это не очень точное, правильнее было бы назвать "оператор выбора из двух вариантов, существующей переменной или дефолтного значения", но это было бы слишком длинно. В любом случае, это мудреное название означает, что РНР выбирает из двух вариантов, "объединяет" их: если переменная есть, то используется её значение, если переменной нет или она равна null - то используется значение, указанное после ??. Отдельно следует отметить, что в приведенном написании (if ($next['referer'] ?? null)) этот оператор не имеет смысла, поскольку нам не нужно возвращать никакое значение, а нужно лишь узнать, установлена ли переменная $next['referer']. В этом случае правильнее будет явно вызвать функцию isset(): if (isset($next['referer'])) это повысит осмысленность и читабельность кода. Поскольку код должен делать только то, что нужно, и в нем не должно быть бессмысленных участков. Правильное применение данного оператора - это использование возвращаемого значения, например $username = $_GET['user'] ?? 'nobody'; // или echo $_GET['user'] ?? ''; Вся эта история придумана для того, чтобы избежать ошибки "Notice: Undefined variable/index/offset" с наименьшим количеством кода. Но следует при этом помнить, что большинство пользователей РНР не понимают смысла этой ошибки, и считают её досадной помехой, от которой надо избавляться любыми средствами. Разумеется, это не так. Как и любое сообщение об ошибке, это предупреждение сигнализирует программисту о возможных проблемах в коде. И поэтому бездумное подавление этой ошибки путем применения оператора ?? оказывается столь же вредным, как и использование оператора @. Функции isset(), empty() и оператор объединения с null следует применять только в том случае, если заведомо ожидается, что переменной может не быть. Если же переменная должна быть, то этот оператор применять не следует, а вместо этого надо дать РНР сообщить об ошибке. Классический пример неправильного использования - это обработка текстовых полей HTML формы. Все поля HTML формы, за исключением чекбоксов и радиокнопок всегда в обязательном порядке передаются на сервер. То есть, проверять их на существование не нужно. Если возникнет ошибка "Undefined index" - то либо у нас опечатка в имени поля/индексе массива в РНР, либо форма была подделана (с ошибками). В обоих случаях дальнейшая обработка формы будет бессмысленной, а выдача ошибки - единственно правильным сценарием.Ответ 2
Это замена if(isset()) - else. Появилось в PHP 7. // Извлекаем значение $_GET['user'], а если оно не задано, // то возвращаем 'nobody' $username = $_GET['user'] ?? 'nobody'; // Это идентично следующему коду: $username = isset($_GET['user']) ? $_GET['user'] : 'nobody'; Подробнее: http://php.net/manual/ru/migration70.new-features.php#migration70.new-features.null-coalesce-opОтвет 3
Это оператор объединения с null ?? - Он возвращает первый операнд, если он задан и не равен NULL, а в обратном случае возвращает второй операнд: if($next['referer'] ?? '') { } if($next['name'] ?? $next['email'] ?? $next['theme'] ?? $next['text'] ?? '') { } Мы так-же можем это определить в переменных, а дальше проверять как нужно. $name = $next['name'] ?? ''; $email = $next['email'] ?? ''; $theme = $next['theme'] ?? ''; $text = $next['text'] ?? ''; if(!$name) { //... } else if(!$email) { //... } else if(!$theme) { //... } else if(!$text) { //... } else { //... } ?? - данный оператор работает только на php 7 и выше, в версиях ниже: if(empty($next['submit'])) { //переменная пуста } if(!empty($next['submit'])) { //переменная не пуста } isset работает немного по другому, советую посмотреть таблицу сравнения типов. На заметку: Поддерживает оператор and so on. if(isset($next['name'], $next['email'], $next['theme'], $next['text'])) { //... } empty и isset разные конструкции языка, но выполняют одинаковую роль, проверку переменной на ее существование, только лишь empty проверяет ее более строго, чем isset и нет такого прототипа, как имеет isset - bool isset ( mixed $var [, mixed $... ] ), где $... - и есть and so on (и так далее...), а в empty такого к сожалению нет. В php 7 мы также можем определять свои методы и функции: func(string ...$var){//...}, вы задействуете оператор and so on (и так далее...) и сможете передавать неограниченное количество аргументов типа string или вообще любой тип убрав задаваемый тип переменной func(...$var). В ранних версиях php, также есть тернарный оператор, который заменяет конструкцию if-else: $if = true; $echo = 'Good!'; echo $if ? $echo : 'Empty!'; Если вдруг - переменной $if не будет существовать или ранее удалится через unset($if), перед выводом через тернарный оператор, будет выведено уведомление (Notice) о том, что переменная не определена ранее, тут то и понадобится isset или empty, чтобы избежать Notice уведомлений: $if = true; $echo = 'Good!'; unset($if); echo isset($if) ? $echo : 'Empty!'; В php 5.3 появилось сокращение тернарного оператора в виде ?:: $if = ''; $echo = 'Good!'; echo $if ?: $echo; // Good! Но без проверки через isset, empty или ?? (null coalescing) вы будете ловить Notice (уведомления о несуществующих переменных или константах, если вдруг напишите $next[referer] без кавычек внутри ['referer']).
Комментариев нет:
Отправить комментарий