Php

Введение

Для начала, вот как атрибут будет выглядеть в коде:


Я думаю, что events subscriber — хороший пример, чтобы объяснить использование атрибутов.  

Кроме того, да, я знаю, синтаксис может быть не таким, как мы этого хотели или надеялись. Возможно, лучше всего было использовать @, или @:, или докблоки, как вариант … Но атрибуты завершены, они с нами останутся такими, поэтому придется справляться с ними в таком виде. Единственное, что стоит упомянуть о синтаксисе, — это то, что все варианты были обсуждены, и есть очень веские причины, по которым был выбран именно этот синтаксис. Вы можете прочитать краткое резюме об этом , или прочитать всю дискуссию о RFC в internals list.

Прежде всего, пользовательские атрибуты — это простые классы, аннотируемые самим атрибутом <<Attribute>>. Вот как это будет выглядеть:

Вот и все — довольно просто, верно? Имейте в виду атрибуты предназначены только для добавления метаданных к классам и методам, не более того. Они не должны и не могут использоваться, например, для проверки ввода аргументов. Другими словами: у вас не будет доступа к параметрам, переданным методу в его атрибутах.

Был RFC, который позволял такое поведение, но этот RFC определенно сделал подход к атрибутам более простыми.

Вернемся к нашему примеру подписчика: нам все еще нужно прочитать метаданные и зарегистрировать наших подписчиков где-нибудь. Исходя из опыта Laravel, я бы использовал service provider для этого, но не стесняйтесь придумывать другие решения.

Вот скучная шаблонная настройка, просто чтобы обеспечить небольшой контекст:

Обратите внимание, что это просто деструктуризация массива. Теперь давайте поближе посмотрим resolveListeners, где и происходит волшебство:. Вы можете видеть, что мета-данные теперь проще читать по сравнению с анализом докблока

Есть две тонкости, которые стоит рассмотреть

Вы можете видеть, что мета-данные теперь проще читать по сравнению с анализом докблока. Есть две тонкости, которые стоит рассмотреть.

Сначала производится вызов $attribute->newInstance(). Здесь создается наш класс пользовательских атрибутов. Он будет принимать параметры, перечисленные в определении атрибута в нашем классе подписчика, и передавать их конструктору.

Конечно технически, вам даже не нужно создавать пользовательский атрибут. Вы можете вызвать $attribute->getArguments() напрямую. Тем не менее, вам все равно нужен пользовательский класс, иначе возникнет ошибка. Более того, создание экземпляра класса означает, что вы получаете гибкость конструктора для ввода разбора любым удобным для вас способом. В целом я бы сказал, что было бы хорошо всегда создавать экземпляр атрибута с помощью newInstance().

Второе, что стоит упомянуть, это использование функции ReflectionMethod::getAttributes(), которая возвращает все атрибуты для метода. Вы можете передать ему два аргумента, чтобы отфильтровать его вывод.

Чтобы понять эту фильтрацию, нужно еще кое-что узнать об атрибутах. Возможно, это было очевидно для вас, но я все равно хотел бы упомянуть об этом: возможно добавить несколько атрибутов к одному и тому же методу, классу, свойству или константе.

Вы могли бы, например, сделать это:

Имея это в виду, понятно, почему от Reflection*::getAttributes() возвращается массив, поэтому давайте посмотрим, как его выходные данные могут быть отфильтрованы.

Допустим, вы анализируете маршруты контроллера, вас интересует только Route атрибут. Вы можете легко передать этот класс в качестве фильтра:

Второй параметр изменяет способ фильтрации. Вы можете передать ReflectionAttribute::IS_INSTANCEOF, что вернет все атрибуты, реализующие данный интерфейс.

Например, если вы анализируете определения контейнеров, основанные на нескольких атрибутах, вы можете сделать что-то вроде этого:

Приоритет и ассоциативность операторов

Во втором выражении пост-инкремент «++» снова имеет более высокий приоритет, нежели «+»:

И «+» является лево-ассоциативным оператором, поэтому левый «+» формирует отдельную группу:

Примечание переводчика: код из оригинальной статьи представлял примеры выражений и не являлся валидным, поэтому он был несколько скорректирован.


Что же это говорит нам о порядке вычисления? Ничего. Приоритет и ассоциативность операторов определяют группировку, но они не говорят о том, в каком порядке эти группы будут выполняться. В частности, в последнем примере, как , так и может быть выполнено в первую очередь.

В PHP на самом деле не определено что же произойдет. Одна версия PHP может выдать вам один результат, а другая — другой. Не пишите код, который зависит от какого-то определенного порядка вычисления выражения.

Самое интересное в PHP 8 +83

  • 19.12.19 10:02

• olegbunin • #481092 • Хабрахабр • •

16400

Программирование, Высокая производительность, PHP, Блог компании Конференции Олега Бунина (Онтико), Zend Framework

PHP 7.4 только-только объявлена stable, а нам уже подавай еще больше усовершенствований. И лучше всех о том, что ждет PHP, может рассказать Дмитрий Стогов — один из ведущих разработчиков Open Source PHP и, наверное, старейший активный контрибьютор. Все доклады Дмитрия только о тех технологиях и решениях, над которыми он работает лично. В лучших традициях Онтико под катом текстовая версия рассказа о самых интересных с точки зрения Дмитрия нововведениях PHP 8, которые могут открыть новые use-case-ы. В первую очередь JIT и FFI — не в ключе «потрясающих перспектив», а с подробностями реализации и подводными камнями.

Для справки:выразили

JIT

Это технология позволяет компилировать части кода в машинный код во время исполнения. Т.е. сначала ваш скрипт запускается интерпретатором, но по мере сбора статистики использования, какие-то самые нагруженные части кода будут компилироваться в машинный код, что позволит сильно ускориться со временем.

Является ли это киллер-фичей? Как бы да, но… По-моему, не особо. Проблемы, описанные выше это никак не решает. И я не видел, чтобы PHP использовали или планировали использовать как числодробилку. C, C++, Rust все равно будут подходить лучше и работать в разы быстрее. Т.е. имхо ускорение которое мы увидели в PHP7.* по сравнению с PHP5 — уже и так крутое. PHP и так один из самых быстрых скриптовых языков, быстрее чем Ruby и Python. Я очень уважаю команду PHP и Дмитрия Стогова в частности, но по-моему титанические усилия по добавлению JIT в PHP не совсем оправданы для реальных php-приложений.

Если честно, я бы предпочел, чтобы вместо этого был сделан шаг в сторону асинхронных возможностей. Какие-нибудь аналоги Async/await и Promise.

Новая функцияp get_resource_id()

Ресурсы — это специальные переменные в PHP, ссылающиеся на внешние ресурсы. Например, соединение MySQL, или дескриптор файла.

Каждому из этих ресурсов присваивается идентификатор, хотя ранее единственным способом узнать, что это идентификатор, было преобразование ресурса в int:

PHP 8 добавляет функцию get_resource_id(), делая эту операцию более очевидной и безопасной для типов:

Улучшение абстрактных методов трейтов 

Трейты — это «механизм повторного использования кода в языках с единичным наследованием, таких как PHP». Обычно они используются для объявления методов, которые можно использовать в нескольких классах. Трейты так же могут содержать абстрактные методы, которые должны быть реализованы классами, использующими их. Однако есть предостережение: до PHP 8 сигнатура этих реализаций методов не проверялась. Следующее было действительным:

PHP 8 будет выполнять правильную проверку подписи метода при использовании свйоства и реализации его абстрактных методов. Это также означает, что подписи методов должны совпадать. Другими словами, тип и количество требуемых аргументов должны быть одинаковыми:

Как бы то ни было, по словам автора RFC Никиты Попова , проверка подписи в настоящее время применяется только точечно:

  • Это не применяется в наиболее распространенном случае, когда реализация метода обеспечивается в используемом классом
  • Это принудительно, если реализация исходит из родительского класса
  • Это принудительно, если реализация исходит от дочернего класса

Подытожим историю

Прежде чем углубляться в детали, давайте рассмотрим, как в наши дни разрабатывается язык PHP. Сейчас мы находимся на версии PHP 7.4, а следующей версией станет PHP 8.0, которая выйдет в конце 2020 года.

Начиная с поздних версий 5. *, основная команда старается поддерживать постоянный годовой цикл выпуска и преуспела в этом в течение последних четырех лет.

В целом, каждый новый выпуск активно поддерживается в течение двух лет и получает еще один год «только исправлений безопасности». Цель состоит в том, чтобы побудить разработчиков оставаться в курсе как можно больше: обновляться потихоньку каждый год гораздо легче, чем, например, резкий переход от 5.4 до 7.0.

PHP 5.6 была последней версией 5. * перед выпуском 7.0. Если вы хотите узнать, что случилось с PHP 6, вы можете прослушать этот эпизод подкаста PHP Roundtable.

Разработка PHP в настоящее время осуществляется группой добровольцев, некоторые из которых получают заработную плату от своих работодателей, чтобы они работали над основной работой. Большая часть обсуждения того, как развивается язык, происходит в списке рассылки.

Historical issues

autoconf and libtool information for PHP 5.3 and below

There seem to be problems with libtool 1.4.2. It is suggested that you use libtool 1.4, along with autoconf 2.13 and automake 1.4. You should also ensure that autoconf, automake and libtool are installed in the same directory. libtool 1.5 will not work.

The following combinations are known to work with PHP 5.3 and below:

  • autoconf 2.13, automake 1.4 and libtool 1.4.3
  • autoconf 2.13, automake 1.5 and libtool 1.4.3

Since PHP 4.3 automake and its aclocal program are no longer needed to build PHP.

If you have multiple versions of autoconf installed on your computer, as is common for many UNIXes, you can set the PHP_AUTOCONF and PHP_AUTOHEADER variables when running buildconf to indicate which versions it should use e.g.:

Zend/zend_language_scanner.c: No such file or directory

PHP only supports flex 2.5.4, not later versions as they broke backwards compatibility. Please note that PHP 5.3 and later do not require flex at all.

The Case for JIT Today

Even though most of the fundamentals for JIT-enabling PHP haven’t changed — we believe there is a good case today for JIT-enabling PHP.

First, we believe we’ve reached the extent of our ability to improve PHP’s performance using other optimization strategies. In other words — we can’t further improve the performance of PHP unless we use JIT.

Secondly — using JIT may open the door for PHP being more frequently used in other, non-Web, CPU-intensive scenarios — where the performance benefits will actually be very substantial — and for which PHP is probably not even being considered today.

Lastly — making JIT available can provide us (with additional efforts) with the ability to develop built-in functions in PHP, instead of (or in addition to) C — without suffering the huge performance penalty that would be associated with such a strategy in today’s, non-JITted engine. This, in turn, can open the door to faster innovation — and also more secure implementations, that would be less susceptible to memory management, overflows and similar issues associated with C-based development.

FFI — Foreign Function Interface

  • Это 1000 новых способов выстрелить себе в ногу.
  • Требует знания С и иногда ручного управления памятью.
  • Не поддерживает С-препроцессор (#include, #define, …) и С++.
  • Производительность без JIT достаточно низкая.

только в командной строке

FFI + preloading

Работа со структурами данных С

  • Нейронные сети на PHP.
  • Компилятор на PHP.

К сожалению, скорость работы FFI пока оставляет желать лучшего.

Native Arrays FFI Arrays
PyPy 0,010 0,081
Python 0,212 0,343
LuaJIt -joff 0,037 0,412
LuaJit -jon 0,003 0,002
PHP 0,040 0,093
PHP + JIT 0,016 0,087

Автор выражает благодарность: Zeev Surasky (Zend), Andi Gutmans (ex-Zend, Amazon), Xinchen Hui (ex-Weibo, ex-Zend, Lianjia), Nikita Popov (JetBrains), Anatol Belsky (Microsoft), Anthony Ferrara (ex-Google, Lingo Live), Joe Watkins, Mohammad Reza Haghighat (Intel) и команду Intel, Andy Wingo (JS hacker, Igalia), Mike Pall (автор LuaJIT).этого

Создать DateTime объекты из интерфейса


Вы уже можете создать DateTime объект из DateTimeImmutable объекта, используя DateTime::createFromImmutable($immutableDateTime), но наоборот было сложно. Добавление DateTime::createFromInterface() и DatetimeImmutable::createFromInterface() теперь позволяет получить обобщенный способ конвертировать DateTimeи DateTimeImmutable объекты друг в друга.

Новый Stringable интерфейс

Появится новый интерфейс Stringable, который автоматически добавляется в классы, которые реализуют магический метод __toString(), и нет необходимости реализовывать его вручную. 

У данный RFC две цели:

  • разрешить использовать, string|Stringable чтобы выразить string|object-with-__toString()
  • предоставить прямой путь обновления с PHP 7 до 8

Steps for using PHP from Git

  1. You can retrieve the PHP source code from our GitHub mirror with this command:

    Alternatively, you can retrieve the source code from git.php.net with this command:

    You can also download a snapshot from GitHub:

    • Go to the php-src project page.
    • Select the branch you’re interested in from the branch dropdown.
    • Click on the Download ZIP button.
  2. Make sure you’re in the right directory to work on PHP:
  3. You can then check out the branch you want to build, for example: PHP 7.1: PHP 7.2: PHP 7.3: PHP 7.4: PHP HEAD:
  4. Note that certain combinations of autoconf and libtool may not work when used together, particularly with historical versions of PHP. See for details. Also, certain versions of autoconf may generate warnings of . These messages can usually be ignored.

  5. Run to generate the configure script. This may take several moments.
  6. From this point onwards, installation is similar to the installation of one of the official packages with one main difference – you will need . You may also require re2c if you intend to change any of the scanner and parser files PHP uses.

There are many other things, such as the XML source code for the documentation, available via Git. See the web-based view of the Git server to see what is available.

The PHP Wiki has a useful Git FAQ, which provides useful tips and cheatsheets for using the PHP Git repository, and if you want to become involved in developing PHP, the Git Workflow page is also likely to be of interest.

Так и зачем нам это?

Если после всего выше написанного вы думаете, что JIT предлагает небольшие краткосрочные преимущества для ваших веб-приложений, вы совершенно правы. Трудно сказать, какое влияние это окажет на производительность приложения, прежде чем выйдет окончательный релиз и разработчики не опробуют его в боевых реалиях.

Конечно не будучи экспертом в этой области, все это кажется очень сложным, но очень интересно видеть как такие вещи движутся в мире PHP. Мне очень любопытно, куда этот путь приведет. Это может сделать PHP более жизнеспособным выбором для таких ресурсоемких процессов, как, например, машинное обучение, 3D-рендеринг, 2D (графический интерфейс) и анализ данных, и это лишь некоторые из них.

Новый тип mixed v2

С добавлением скалярных типов в PHP 7, обнуляемых в 7.1, объектов в 7.2 и, наконец, типов объединения в 8.0, люди, пишущие код PHP, могут явно объявлять информацию о типах для большинства параметров функции, возвращаемых функций, а также свойств класса. Однако в PHP не всегда поддерживаются типы, и, скорее всего, он всегда будет позволять опускать информацию о типах. Но это приводит к проблеме того, что ее значение неоднозначно, когда отсутствует информация о типе:

  • Функция не возвращает ничего или null
  • Мы ожидаем один из нескольких типов
  • Мы ожидаем, тип, который не может быть подсказан в PHP

Из-за причин, приведенных выше, хорошо, что тип mixed был наконец добавлен, Сам по себе mixed означает один из этих типов:

  • array
  • bool
  • callable
  • int
  • float
  • null
  • object
  • resource
  • string

Обратите внимание, что mixed также может использоваться как параметр или тип свойства, а не только как тип возвращаемого значения. Также обратите внимание, что, поскольку mixed уже включает в себя null, это не может сделать его обнуляемым. Следующее вызовет ошибку:. Throw выражения

Throw выражения

Поскольку в PHP оператор throw не может создавать исключения в тех местах, где разрешены только выражения, такие как функции стрелок, оператор объединения и тернарный оператор. Этот RFC предлагает преобразовать утверждение throw в выражение, чтобы эти случаи стали возможными.

Есть и другие места, где он может быть использован, которые являются более спорными. Эти случаи разрешены в данном RFC

Proposed Voting Choices

Support for JIT is more a strategic PHP question. JIT definitely requires a lot of work, but it may be actively developed only as a part of PHP, with common effort.

This project requires a 2/3+1 majority. Voting opened 2019-03-21 and closes 2019-03-28.

As PHP 7.4 is already branched and its engine is not expected to be significantly changed (consequently requiring corresponding changes to the JIT implementation), we can also consider including JIT in PHP-7.4 as an experimental feature (disabled by default), to provide early access and receive more feedback. This also requires a 2/3+1 majority.

In case JIT is not included in PHP-7.4 and PHP-8 introduces language compatibility breaks (it already does), existing applications couldn’t be tested with JIT without porting to PHP-8.

Синтаксис PHP

Эра 7.* сделала много хорошего, сделав PHP более зрелым языком, когда дело касается синтаксиса языка. Чтобы проиллюстрировать это, я сделал не полный список новых вещей в PHP.

Деструктуризация массива:

Нулевой коалесцирующий оператор:

Оператор присваивания с нулевым слиянием:

Распаковка массива:

Вариадические функции:

Аргумент распаковки:

Типизированные свойства:

Стрелочные функции, также называемые короткими замыканиями:

Генераторы:


И многое другое. Я надеюсь, что из этого списка ясно, что PHP все еще развивается сегодня, и вы можете быть уверены, что это не предел, и дальше будет лучше.

Как это работает?

Есть так называемый «монитор», который будет смотреть на код во время его работы. Когда этот монитор обнаруживает повторяющиеся части вашего кода, он помечает эти части как «теплые» или «горячие», в зависимости от частоты использования.

Эти горячие части могут быть скомпилированы как оптимизированный машинный код и использоваться на лету, в нужный момент, вместо реального кода. Конечно на самом деле все гораздо сложнее, если вы хотите узнать больше, вы можете чекнуть ускоренный курс Mozilla в JIT-компиляторах.

Для этого поста в блоге достаточно понять, что JIT-компилятор может значительно улучшить производительность вашей программы…ну или нет :))

Зеев Сураски, один из разработчиков ядра PHP, недавно продемонстрировал демо с генерацией фракталов:

Необычно для PHP, не правда ли? «Слон в комнате»: Часто ли вы видели, чтобы PHP использу для создания фрактальных анимаций :)))

Зная, что JIT-компилятор пытается идентифицировать «горячие» части вашего кода, вы можете догадаться, почему он оказывает такое влияние на фрактальный пример: множество одних и тех же вычислений происходит снова и снова.

Однако, поскольку PHP чаще всего используется при создании веб-приложений, мы также должны измерить влияние JIT именно на эту область.

А оказывается, что во время обработки веб-запроса кода гораздо меньше. Это не означает, что JIT вообще не может улучшить производительность сети, но мы уже не увидим подобных улучшений, как в случае с фрактальным примером. Дело в том, что в большинстве случаев PHP-приложения ограничены по вводу-выводу (I/O bound, обработка сетевых соединений, чтение и запись файлов, обращение к СУБД, кэширование и т.п.), а JIT лучше всего работает с кодом, который ограничен по процессору (CPU bound).

Это причина, чтобы отказаться от JIT? Точно нет! Есть веские аргументы, чтобы добавить его, хотя это может и не оказать должного влияния на производительность, на которую мы все же надеемся.

Это достаточно веские аргументы в пользу JIT. К сожалению, есть аргументы и против JIT:

— Сложность в обслуживании

Поскольку JIT генерирует машинный код, вы можете представить его как достаточно сложный материал для понимания «программистом языка более высокого уровня».

Имея машинный код в качестве вывода, будет сложнее отлаживать возможные ошибки в JIT-компиляторе PHP. К счастью, есть инструменты, помогающие отладке. Но все же, это машинный код.

Скажем, в JIT-компиляторе есть ошибка, вам нужен разработчик, который знает, как ее исправить. Дмитрий Стогов — тот, кто до сих пор делал большую часть кода, и да, надо помнить, что разработка ядра PHP осуществляется на добровольной основе сообществом контрибьюторов.

Так вот, на сегодняшний день, лишь несколько человек могут поддерживать такую ​​кодовую базу, поэтому вопрос о том, можно ли поддерживать компилятор JIT должным образом, кажется оправданным.

Конечно, люди могут узнать, как работает компилятор. Но это все же сложный материал. Прямо сейчас он насчитывает около 50+ тысяч строк кода

И обратите внимание: это не обычная база кодов клиент-веб-приложение. Это почти-так-же-близко-как-программирования-CPU

Опять же, это не должно быть причиной отказа от JIT, но стоимость обслуживания должна быть тщательно продумана.

Стоит упомянуть еще одну деталь:

Кроссплатформенность. Начиная с последних версий, JIT также работает в Windows и Mac! Большой шаг вперед.


С этим читают