Прежде всего, я знаю, что этот вопрос не раз повторялся здесь:
Но чем больше я исправляю все E_NOTICE (как говорят вам люди), тем больше я замечаю, что:
Возьмем пример:
Скажите, что вы используете PHP-драйвер MongoDB, и у вас есть объект MongoDate
в классе var с именем ts
в классе, который представляет одну строку в коллекции в вашей базе данных. Теперь вы получаете этот var как: $obj->ts->sec
но PHP генерирует соответствие (E_NOTICE), потому что ts
в этом случае не определяется как объект сам по себе, потому что эта конкретная строка не имеет поля ts
. Таким образом, вы считаете, что это нормально, это желаемое поведение, если оно не установлено return null, и я сам позабочусь о нем вне интерпретаторов собственной роботизированной работы (поскольку вы завершаете это в функции date()
которая возвращает 1970
если var – null
или none-object
).
Но теперь, чтобы исправить этот E_NOTICE, поскольку другой разработчик действительно хочет, чтобы я с тех пор, как ANY E_NOTICEs является terribad, и это делает код медленнее, чтобы не делать это в соответствии с ошибками. Поэтому я getTs
новую функцию в классе $obj
называемом getTs
и я даю ему 3 строки, буквально ничего не делая, кроме как проверить, является ли ts
var объектом MongoDate
и возвращает его, если он …
ЗАЧЕМ? Не может ли PHP сделать это отлично для меня в гораздо более быстром интерпретаторе, чем делать это во время выполнения самого приложения? Я имею в виду все, где мне приходится добавлять бесполезный бамп к моему коду, довольно пустые функции для обнаружения переменных, которые я на самом деле просто обрабатываю с собственной возможностью PHP возвращать null
или проверять их instanceof
когда мне действительно нужно (когда это жизненно важно для работа и поведение указанной функции), и не заставляйте меня начинать с isset()
Я добавил около 300 строк isset()
s, это выходит из-под контроля. Я, конечно, должен был выполнять эти функции getTs
потому что вы не можете этого сделать:
class obj{ public $ts = new MongoDate(); }
Я либо должен был бы хранить ts
внутри __constructor
(что я тоже не очень доволен, я использую много магии, как есть), либо использую функцию для определения, установлено ли это (что я сейчас делаю).
Я имею в виду, я понимаю, почему я должен исправить:
null
vars) Но если вы протестировали свой код, и знаете, что он безопасен и будет работать только так, как вы хотите, то, что нужно для исправления всех undefined index
или ошибок без none-object
? Не добавляет ли набор функций isset()
s и 2 строки в ваш код на самом деле микро-оптимизации?
Я заметил после того, как сделал половину моего сайта E_NOTICE совместимым, что на самом деле он использует больше процессора, памяти и времени сейчас … так что с чем бороться с каждой ошибкой E_NOTICE, а не только с ошибками ARE?
Спасибо за ваши мысли,
Независимо от того или нет, вы должны исправить их, конечно, спорно, и будет только зависеть от возвращения в вашей ситуации; например, более важно, если код будет иметь более длительный срок службы, больше разработчиков и т. д.
В общем, если предположить, что ваши функции будут использоваться (и неправильно использованы) кем-то другим, это лучшая практика, поэтому вы должны выполнить isset /! Empty / is_object для проверки этого. Часто ваш код найдет способ использования и ситуации, для которых вы никогда не предназначались.
Что касается производительности, каждый раз, когда возникает какая-либо ошибка – включен E_NOTICE – интерпретатор запускает обработчик ошибок, строит трассировку стека и форматирует ошибку. Дело в том, что, независимо от того, имеете ли вы их отчетность, ошибки всегда замедляют выполнение; поэтому 2-3 вызова функций, чтобы избежать E_NOTICE, все равно улучшат вашу производительность .
Изменить: альтернативы для приведенного выше примера
Я бы не стал создавать дополнительные объекты, чтобы избежать ошибок; вы можете изящно избегать их. Вот несколько вариантов:
1) Функция, которая обрабатывает отсутствующие ts:
SpecialClass class { funciton getTs () { return !empty($this->ts) ? $ts->sec : false; } }
2) Сделка с отсутствующими ts в шаблоне / процедуре:
if (!empty($obj->ts->sec)) { //do something }
Мне особенно нравится empty()
потому что вы можете использовать его для замены (isset($var) && ($var or 0 != $var //etc))
, Сохраняя несколько вызовов / сравнений и пустые никогда не выдает уведомления для целевого var или атрибут. Это вызовет ошибку, если вы вызываете ее в простейшей / член несуществующей переменной.
Вы действительно получаете лучшую производительность, используя isset()
. Я сделал несколько тестов не так давно, и только скрытые ошибки вышли примерно на 10 раз медленнее.
http://garrettbluma.com/2011/11/14/php-isset-performance/
Тем не менее, производительность обычно не является критическим фактором в PHP. Что лично меня сводит с ума, это бесшумные ошибки .
Когда интерпретатор предпочитает не отмечать что-то как ошибку (что может привести к нестабильности), это огромная проблема. В частности, PHP имеет тенденцию
Возможно, я просто слишком самоуверен в этом, но я был укушен этими молчаливыми ошибками. Я рекомендую всегда включать E_NOTICE в отчет об ошибках.