Что замыкают замыкания PHP в операторах IF?

Моя цель – поставить сложную логику в оператор if (). Предположим, у меня есть массив значений, и я собираюсь выполнить немного кода, если все в моем массиве отличное от нуля. Обычно я могу сказать: $valid = true , foreach my array и set $valid = false когда найден нуль. Тогда я запустил бы свой код, if ($valid) . В качестве альтернативы, я мог бы включить мой цикл в функцию и поместить функцию intop my if() .

Но я ленив, поэтому я бы предпочел не гадать с кучей «правильных» флагов, и я бы предпочел написать совершенно новую функцию, которая используется только в одном месте.

Итак, скажем, у меня есть это:

 if ($q = function() { return 'foo'; }) { echo $q; } else { echo 'false'; } 

Я ожидал, что if получит 'foo' , который оценивается как true. Мое закрытие привязано к $q и оператор выполняется. $q возвращает строку foo , и 'foo' печатается.

Вместо этого я получаю ошибку. Object of class Closure could not be converted to string .

Итак, давайте попробуем это:

 if (function() { return false; }) { echo 'foo'; } else { echo 'true'; } 

Я ожидал, что моя функция вернет false, и «true» будет напечатано. Вместо этого печатается «foo».

Что не так в том, как я это делаю? Похоже, он говорит: «Да, это определенно функция!» вместо «Нет, потому что функция вычисляется как false». Есть ли способ сделать то, что я пытаюсь сделать?

Related of "Что замыкают замыкания PHP в операторах IF?"

function() { return false; } function() { return false; } создает объект типа Closure , аналогичный new с другими типами классов, сравнивает следующий код:

 $func = function() { return false; }; 

$func теперь является объектом. Каждый объект возвращает true в if . Так

 if ($func) { # true } else { # will never go here. } 

Возможно, вы захотите сделать это:

 if ($func()) { # true } else { # false } 

который вызовет объект Closure $func и даст его возвращаемое значение.

Оба они оценивают истину.

Вы должны заставить функцию выполнить ее использовать в инструкции if.

Попробуй это:

 $q = function() { return false; }; if ($q()) { //should not go here. echo $q(); } else { echo 'false'; } 

Демо: http://codepad.viper-7.com/Osym1s

Закрытия PHP реализованы как хак-объекты типа Closure . Ваш код фактически создает экземпляр объекта этого класса и присваивает его $ q. В PHP результат присваивания – это назначаемое значение, поэтому, по сути, код сводится к

 if (new Closure()) { ... } 

Вы не выполняете закрытие, когда вы вызываете echo , поэтому он пытается распечатать закрытие, а не результат закрытия:

 echo $q(); 

Вы создаете анонимную функцию, но не выполняете ее. Когда вы проверяете $q = function() { return 'foo'; } $q = function() { return 'foo'; } , вы говорите: «Назначьте ссылку на эту анонимную функцию на $ q и передайте этот тест, если $ q не является нулевым» (не PHP весело?)

Вы должны вызвать закрытие и назначить его результат до $q перед тестированием и повторить $q .