xref: /web-php/releases/8.0/ru.php (revision c093fb53)
1<?php
2$_SERVER['BASE_PAGE'] = 'releases/8.0/ru.php';
3include_once __DIR__ . '/common.php';
4
5releases\php80\common_header(
6    'PHP 8.0 — большое обновление языка PHP. ' .
7    'Оно содержит множество новых возможностей и оптимизаций, ' .
8    'включая именованные аргументы, тип union, атрибуты, ' .
9    'упрощённое определение свойств в конструкторе, выражение match, ' .
10    'оператор nullsafe, JIT и улучшения в системе типов, ' .
11    'обработке ошибок и консистентности.');
12
13?>
14<section class="php8-section php8-section_dark php8-section_header center">
15  <div class="page-tools">
16    <div class="change-language">
17        <?php releases\php80\language_chooser('ru'); ?>
18    </div>
19  </div>
20  <div class="php8-section__content">
21    <div class="php8-logo">
22      <img src="/images/php8/logo_php8.svg" alt="php8" height="126" width="343">
23    </div>
24    <div class="php8-title">доступен!</div>
25    <div class="php8-subtitle">
26      PHP 8.0 — большое обновление языка PHP.<br class="display-none-md"> Оно содержит множество новых возможностей и
27      оптимизаций, включая именованные аргументы, union type, атрибуты, упрощённое определение свойств в конструкторе, выражение match,
28      оператор nullsafe, JIT и улучшения в системе типов, обработке ошибок и консистентности.
29    </div>
30    <div class="php8-button-wrapper center">
31      <a class="php8-button php8-button_light" href="/downloads">Переходите на PHP 8!</a>
32    </div>
33  </div>
34</section>
35
36<section class="php8-section center">
37  <div class="php8-compare">
38    <h2 class="php8-h2" id="named-arguments">
39      Именованные аргументы
40      <a class="php8-rfc" href="https://wiki.php.net/rfc/named_params">RFC</a>
41    </h2>
42    <div class="php8-compare__main">
43      <div class="php8-compare__block example-contents">
44        <div class="php8-compare__label">PHP 7</div>
45        <div class="php8-code phpcode">
46            <?php highlight_php_trimmed(
47                'htmlspecialchars($string, ENT_COMPAT | ENT_HTML401, \'UTF-8\', false);',
48            );?>
49        </div>
50      </div>
51      <div class="php8-compare__arrow"></div>
52      <div class="php8-compare__block example-contents">
53        <div class="php8-compare__label php8-compare__label_new">PHP 8</div>
54        <div class="php8-code phpcode">
55            <?php highlight_php_trimmed(
56                'htmlspecialchars($string, double_encode: false);',
57            );?>
58        </div>
59      </div>
60    </div>
61    <div class="php8-compare__content">
62      <ul>
63        <li>Указывайте только необходимые параметры, пропускайте необязательные.</li>
64        <li>Порядок аргументов не важен, аргументы самодокументируемы.</li>
65      </ul>
66    </div>
67  </div>
68
69  <div class="php8-compare">
70    <h2 class="php8-h2" id="attributes">
71      Атрибуты
72      <a class="php8-rfc" href="https://wiki.php.net/rfc/attributes_v2">RFC</a> <a class="php8-rfc" href="/manual/ru/language.attributes.php">Документация</a>
73    </h2>
74    <div class="php8-compare__main">
75      <div class="php8-compare__block example-contents">
76        <div class="php8-compare__label">PHP 7</div>
77        <div class="php8-code phpcode">
78            <?php highlight_php_trimmed(
79                'class PostsController
80{
81    /**
82     * @Route("/api/posts/{id}", methods={"GET"})
83     */
84    public function get($id) { /* ... */ }
85}',
86            );?>
87        </div>
88      </div>
89      <div class="php8-compare__arrow"></div>
90      <div class="php8-compare__block example-contents">
91        <div class="php8-compare__label php8-compare__label_new">PHP 8</div>
92        <div class="php8-code phpcode">
93            <?php highlight_php_trimmed(
94                'class PostsController
95{
96    #[Route("/api/posts/{id}", methods: ["GET"])]
97    public function get($id) { /* ... */ }
98}',
99            );?>
100        </div>
101      </div>
102    </div>
103    <div class="php8-compare__content">
104      <p>Вместо аннотаций PHPDoc вы можете использовать структурные метаданные с нативным синтаксисом PHP.</p>
105    </div>
106  </div>
107
108  <div class="php8-compare">
109    <h2 class="php8-h2" id="constructor-property-promotion">
110      Объявление свойств в конструкторе
111      <a class="php8-rfc" href="https://wiki.php.net/rfc/constructor_promotion">RFC</a> <a class="php8-rfc" href="/manual/ru/language.oop5.decon.php#language.oop5.decon.constructor.promotion">Документация</a>
112    </h2>
113    <div class="php8-compare__main">
114      <div class="php8-compare__block example-contents">
115        <div class="php8-compare__label">PHP 7</div>
116        <div class="php8-code phpcode">
117            <?php highlight_php_trimmed(
118                'class Point {
119  public float $x;
120  public float $y;
121  public float $z;
122
123  public function __construct(
124    float $x = 0.0,
125    float $y = 0.0,
126    float $z = 0.0
127  ) {
128    $this->x = $x;
129    $this->y = $y;
130    $this->z = $z;
131  }
132}',
133            );?>
134        </div>
135      </div>
136      <div class="php8-compare__arrow"></div>
137      <div class="php8-compare__block example-contents">
138        <div class="php8-compare__label php8-compare__label_new">PHP 8</div>
139        <div class="php8-code phpcode">
140            <?php highlight_php_trimmed(
141                'class Point {
142  public function __construct(
143    public float $x = 0.0,
144    public float $y = 0.0,
145    public float $z = 0.0,
146  ) {}
147}',
148            );?>
149        </div>
150      </div>
151    </div>
152    <div class="php8-compare__content">
153      <p>Меньше шаблонного кода для определения и инициализации свойств.</p>
154    </div>
155  </div>
156
157  <div class="php8-compare">
158    <h2 class="php8-h2" id="union-types">
159      Тип Union
160      <a class="php8-rfc" href="https://wiki.php.net/rfc/union_types_v2">RFC</a> <a class="php8-rfc" href="/manual/ru/language.types.declarations.php#language.types.declarations.composite.union">Документация</a>
161    </h2>
162    <div class="php8-compare__main">
163      <div class="php8-compare__block example-contents">
164        <div class="php8-compare__label">PHP 7</div>
165        <div class="php8-code phpcode">
166            <?php highlight_php_trimmed(
167                'class Number {
168  /** @var int|float */
169  private $number;
170
171  /**
172   * @param float|int $number
173   */
174  public function __construct($number) {
175    $this->number = $number;
176  }
177}
178
179new Number(\'NaN\'); // Нет ошибки',
180            );?>
181        </div>
182      </div>
183      <div class="php8-compare__arrow"></div>
184      <div class="php8-compare__block example-contents">
185        <div class="php8-compare__label php8-compare__label_new">PHP 8</div>
186        <div class="php8-code phpcode">
187            <?php highlight_php_trimmed(
188                'class Number {
189  public function __construct(
190    private int|float $number
191  ) {}
192}
193
194new Number(\'NaN\'); // TypeError',
195            );?>
196        </div>
197      </div>
198    </div>
199    <div class="php8-compare__content">
200      <p>Вместо аннотаций PHPDoc для объединённых типов вы можете использовать объявления типа union, которые
201        проверяются во время выполнения.</p>
202    </div>
203  </div>
204
205  <div class="php8-compare">
206    <h2 class="php8-h2" id="match-expression">
207      Выражение Match
208      <a class="php8-rfc" href="https://wiki.php.net/rfc/match_expression_v2">RFC</a> <a class="php8-rfc" href="/manual/ru/control-structures.match.php">Документация</a>
209    </h2>
210    <div class="php8-compare__main">
211      <div class="php8-compare__block example-contents">
212        <div class="php8-compare__label">PHP 7</div>
213        <div class="php8-code phpcode">
214            <?php highlight_php_trimmed(
215                'switch (8.0) {
216  case \'8.0\':
217    $result = "О нет!";
218    break;
219  case 8.0:
220    $result = "То, что я и ожидал";
221    break;
222}
223echo $result;
224//> О нет!',
225            );?>
226        </div>
227      </div>
228      <div class="php8-compare__arrow"></div>
229      <div class="php8-compare__block example-contents">
230        <div class="php8-compare__label php8-compare__label_new">PHP 8</div>
231        <div class="php8-code phpcode">
232            <?php highlight_php_trimmed(
233                'echo match (8.0) {
234  \'8.0\' => "О нет!",
235  8.0 => "То, что я и ожидал",
236};
237//> То, что я и ожидал',
238            );?>
239        </div>
240      </div>
241    </div>
242    <div class="php8-compare__content">
243      <p>Новое выражение match похоже на оператор switch со следующими особенностями:</p>
244      <ul>
245        <li>Match — это выражение, его результат может быть сохранён в переменной или возвращён.</li>
246        <li>Условия match поддерживают только однострочные выражения, для которых не требуется управляющая конструкция break;.</li>
247        <li>Выражение match использует строгое сравнение.</li>
248      </ul>
249    </div>
250  </div>
251
252  <div class="php8-compare">
253    <h2 class="php8-h2" id="nullsafe-operator">
254     Оператор Nullsafe
255      <a class="php8-rfc" href="https://wiki.php.net/rfc/nullsafe_operator">RFC</a>
256    </h2>
257    <div class="php8-compare__main">
258      <div class="php8-compare__block example-contents">
259        <div class="php8-compare__label">PHP 7</div>
260        <div class="php8-code phpcode">
261            <?php highlight_php_trimmed(
262                '$country =  null;
263
264if ($session !== null) {
265  $user = $session->user;
266
267  if ($user !== null) {
268    $address = $user->getAddress();
269
270    if ($address !== null) {
271      $country = $address->country;
272    }
273  }
274}',
275            );?>
276        </div>
277      </div>
278      <div class="php8-compare__arrow"></div>
279      <div class="php8-compare__block example-contents">
280        <div class="php8-compare__label php8-compare__label_new">PHP 8</div>
281        <div class="php8-code phpcode">
282            <?php highlight_php_trimmed(
283                '$country = $session?->user?->getAddress()?->country;',
284            );?>
285        </div>
286      </div>
287    </div>
288    <div class="php8-compare__content">
289      <p>Вместо проверки на null вы можете использовать последовательность вызовов с новым оператором Nullsafe. Когда
290       один из элементов в последовательности возвращает null, выполнение прерывается и вся последовательность
291        возвращает null.</p>
292    </div>
293  </div>
294
295  <div class="php8-compare">
296    <h2 class="php8-h2" id="saner-string-to-number-comparisons">
297      Улучшенное сравнение строк и чисел
298      <a class="php8-rfc" href="https://wiki.php.net/rfc/string_to_number_comparison">RFC</a>
299    </h2>
300    <div class="php8-compare__main">
301      <div class="php8-compare__block example-contents">
302        <div class="php8-compare__label">PHP 7</div>
303        <div class="php8-code phpcode">
304            <?php highlight_php_trimmed(
305                '0 == \'foobar\' // true',
306            );?>
307        </div>
308      </div>
309      <div class="php8-compare__arrow"></div>
310      <div class="php8-compare__block example-contents">
311        <div class="php8-compare__label php8-compare__label_new">PHP 8</div>
312        <div class="php8-code phpcode">
313            <?php highlight_php_trimmed(
314                '0 == \'foobar\' // false',
315            );?>
316        </div>
317      </div>
318    </div>
319    <div class="php8-compare__content">
320      <p>При сравнении с числовой строкой PHP 8 использует сравнение чисел. В противном случае число преобразуется в
321        строку и используется сравнение строк.</p>
322    </div>
323  </div>
324
325  <div class="php8-compare">
326    <h2 class="php8-h2" id="consistent-type-errors-for-internal-functions">
327      Ошибки согласованности типов для встроенных функций
328      <a class="php8-rfc" href="https://wiki.php.net/rfc/consistent_type_errors">RFC</a>
329    </h2>
330    <div class="php8-compare__main">
331      <div class="php8-compare__block example-contents">
332        <div class="php8-compare__label">PHP 7</div>
333        <div class="php8-code phpcode">
334            <?php highlight_php_trimmed(
335                'strlen([]); // Warning: strlen() expects parameter 1 to be string, array given
336
337array_chunk([], -1); // Warning: array_chunk(): Size parameter expected to be greater than 0',
338            );?>
339        </div>
340      </div>
341      <div class="php8-compare__arrow"></div>
342      <div class="php8-compare__block example-contents">
343        <div class="php8-compare__label php8-compare__label_new">PHP 8</div>
344        <div class="php8-code phpcode">
345            <?php highlight_php_trimmed(
346                'strlen([]); // TypeError: strlen(): Argument #1 ($str) must be of type string, array given
347
348array_chunk([], -1); // ValueError: array_chunk(): Argument #2 ($length) must be greater than 0',
349            );?>
350        </div>
351      </div>
352    </div>
353    <div class="php8-compare__content">
354      <p>Большинство внутренних функций теперь выбрасывают исключение Error, если при проверке параметра возникает ошибка.</p>
355    </div>
356  </div>
357</section>
358
359<section class="php8-section php8-section_light">
360  <h2 class="php8-h2">Компиляция Just-In-Time</h2>
361  <p>
362    PHP 8 представляет два механизма JIT-компиляции. Трассировка JIT, наиболее перспективная из них, на синтетических бенчмарках показывает
363    улучшение производительности примерно в 3 раза и в 1,5–2 раза на некоторых долго работающих приложениях. Стандартная
364    производительность приложения находится на одном уровне с PHP 7.4.
365  </p>
366  <h3 class="php8-h3">
367    Относительный вклад JIT в производительность PHP 8
368  </h3>
369  <p>
370    <img src="/images/php8/scheme.svg" width="900" alt="Компиляция Just-In-Time">
371  </p>
372
373  <div class="php8-columns">
374    <div class="php8-column">
375      <h2 class="php8-h2 php8-h2_margin-top">Улучшения в системе типов и обработке ошибок</h2>
376      <ul>
377        <li>
378          Более строгие проверки типов для арифметических/побитовых операторов
379          <a href="https://wiki.php.net/rfc/arithmetic_operator_type_checks">RFC</a>
380        </li>
381        <li>
382          Проверка методов абстрактных трейтов <a href="https://wiki.php.net/rfc/abstract_trait_method_validation">RFC</a>
383        </li>
384        <li>
385          Правильные сигнатуры магических методов <a href="https://wiki.php.net/rfc/magic-methods-signature">RFC</a>
386        </li>
387        <li>
388          Реклассификация предупреждений движка <a href="https://wiki.php.net/rfc/engine_warnings">RFC</a>
389        </li>
390        <li>
391          Фатальная ошибка при несовместимости сигнатур методов <a href="https://wiki.php.net/rfc/lsp_errors">RFC</a>
392        </li>
393        <li>
394          Оператор @ больше не подавляет фатальные ошибки.
395        </li>
396        <li>
397          Наследование с private методами <a href="https://wiki.php.net/rfc/inheritance_private_methods">RFC</a>
398        </li>
399        <li>
400          Новый тип mixed <a href="https://wiki.php.net/rfc/mixed_type_v2">RFC</a>
401        </li>
402        <li>
403          Возвращаемый тип static <a href="https://wiki.php.net/rfc/static_return_type">RFC</a>
404        </li>
405        <li>
406          Типы для стандартных функций
407          <a href="https://externals.io/message/106522">E-mail Тема</a>
408        </li>
409        <li>
410            Непрозрачные объекты вместо ресурсов для
411            <a href="https://php.watch/versions/8.0/resource-CurlHandle">Curl</a>,
412            <a href="https://php.watch/versions/8.0/gdimage">Gd</a>,
413            <a href="https://php.watch/versions/8.0/sockets-sockets-addressinfo">Sockets</a>,
414            <a href="https://php.watch/versions/8.0/OpenSSL-resource">OpenSSL</a>,
415            <a href="https://php.watch/versions/8.0/xmlwriter-resource">XMLWriter</a>, e
416            <a href="https://php.watch/versions/8.0/xmlwriter-resource">XML</a>
417            расширения
418        </li>
419      </ul>
420    </div>
421    <div class="php8-column">
422      <h2 class="php8-h2 php8-h2_margin-top">Прочие улучшения синтаксиса</h2>
423      <ul>
424        <li>
425          Разрешена запятая в конце списка параметров <a href="https://wiki.php.net/rfc/trailing_comma_in_parameter_list">RFC</a>
426          и в списке use замыканий <a href="https://wiki.php.net/rfc/trailing_comma_in_closure_use_list">RFC</a>
427        </li>
428        <li>
429          Блок catch без указания переменной <a href="https://wiki.php.net/rfc/non-capturing_catches">RFC</a>
430        </li>
431        <li>
432          Изменения синтаксиса переменных <a href="https://wiki.php.net/rfc/variable_syntax_tweaks">RFC</a>
433        </li>
434        <li>
435          Имена в пространстве имен рассматриваются как единый токен <a href="https://wiki.php.net/rfc/namespaced_names_as_token">RFC</a>
436        </li>
437        <li>
438          Выражение Throw <a href="https://wiki.php.net/rfc/throw_expression">RFC</a>
439        </li>
440        <li>
441          Добавление ::class для объектов <a href="https://wiki.php.net/rfc/class_name_literal_on_object">RFC</a>
442        </li>
443      </ul>
444
445      <h2 class="php8-h2 php8-h2_margin-top">Новые классы, интерфейсы и функции</h2>
446      <ul>
447        <li>
448          Класс <a href="https://wiki.php.net/rfc/weak_maps">Weak Map</a>
449        </li>
450        <li>
451          Интерфейс <a href="https://wiki.php.net/rfc/stringable">Stringable</a>
452        </li>
453        <li>
454          <a href="https://wiki.php.net/rfc/str_contains">str_contains()</a>,
455          <a href="https://wiki.php.net/rfc/add_str_starts_with_and_ends_with_functions">str_starts_with()</a>,
456          <a href="https://wiki.php.net/rfc/add_str_starts_with_and_ends_with_functions">str_ends_with()</a>
457        </li>
458        <li>
459          <a href="https://github.com/php/php-src/pull/4769">fdiv()</a>
460        </li>
461        <li>
462          <a href="https://wiki.php.net/rfc/get_debug_type">get_debug_type()</a>
463        </li>
464        <li>
465          <a href="https://github.com/php/php-src/pull/5427">get_resource_id()</a>
466        </li>
467        <li>
468          Объектно-ориентированная функция <a href="https://wiki.php.net/rfc/token_as_object">token_get_all()</a>
469        </li>
470        <li>
471          <a href="https://wiki.php.net/rfc/dom_living_standard_api">Новые API для обходения и обработки DOM</a>
472        </li>
473      </ul>
474    </div>
475  </div>
476</section>
477
478<section class="php8-section php8-section_dark php8-section_footer php8-footer">
479  <div class="php8-section__content">
480    <h2 class="php8-h2 center">
481      Выше производительность, лучше синтаксис, надежнее система типов.
482    </h2>
483    <div class="php8-button-wrapper center">
484      <a class="php8-button php8-button_light" href="/downloads">Переходите на PHP 8!</a>
485    </div>
486    <div class="php8-footer__content">
487      <p>
488        Для загрузки исходного кода PHP 8 посетите страницу <a href="http://www.php.net/downloads">downloads</a>.
489        Бинарные файлы Windows находятся на сайте <a href="http://windows.php.net/download">PHP для Windows</a>.
490        Список изменений представлен в <a href="http://www.php.net/ChangeLog-8.php">ChangeLog</a>.
491      </p>
492      <p>
493        <a href="/manual/ru/migration80.php">Руководство по миграции</a> доступно в разделе документации. Пожалуйста,
494        изучите его для получения подробного списка новых возможностей и обратно несовместимых изменений.
495      </p>
496    </div>
497  </div>
498</section>
499
500
501
502
503<?php site_footer();
504