# 6. Вирази

У цьому розділі пояснюється значення елементів виразів у Python.

Примітки до синтаксису: У цьому та наступних розділах для опису синтаксису буде використано розширену нотацію BNF, а не лексичний аналіз. Коли (одна альтернатива) синтаксичне правило має форму

    name ::=  othername

і семантика не вказана, семантика цієї форми `name` така сама, як і `othername`.

## 6.1. Арифметичні перетворення

Коли в описі арифметичного оператора нижче використовується фраза «числові аргументи перетворюються на загальний тип», це означає, що реалізація оператора для вбудованих типів працює наступним чином:

- Якщо будь-який аргумент є комплексним числом, інший перетворюється на комплексне;

- otherwise, if either argument is a floating-point number, the other is converted to floating point;

- інакше обидва мають бути цілими числами, і перетворення не потрібне.

Деякі додаткові правила застосовуються до певних операторів (наприклад, рядок як лівий аргумент для оператора «%»). Розширення мають визначати власну поведінку перетворення.

## 6.2. Атоми

Атоми є основними елементами виразів. Найпростішими атомами є ідентифікатори або літерали. Форми, укладені в дужки, дужки або дужки, також класифікуються синтаксично як атоми. Синтаксис для атомів:

    atom      ::=  identifier | literal | enclosure
    enclosure ::=  parenth_form | list_display | dict_display | set_display
                   | generator_expression | yield_atom

### 6.2.1. Ідентифікатори (імена)

Ідентифікатор, що зустрічається як атом, є ім’ям. Перегляньте розділ Ідентифікатори та ключові слова для лексичного визначення та розділ Називання та зв’язування для документації іменування та прив’язки.

Коли ім’я пов’язане з об’єктом, оцінка атома дає цей об’єкт. Коли ім’я не прив’язане, спроба його оцінити викликає виняток `NameError`.

#### 6.2.1.1. Private name mangling

When an identifier that textually occurs in a class definition begins with two or more underscore characters and does not end in two or more underscores, it is considered a private name of that class.

Дивись також

The class specifications.

More precisely, private names are transformed to a longer form before code is generated for them. If the transformed name is longer than 255 characters, implementation-defined truncation may happen.

The transformation is independent of the syntactical context in which the identifier is used but only the following private identifiers are mangled:

- Any name used as the name of a variable that is assigned or read or any name of an attribute being accessed.

  The `__name__` attribute of nested functions, classes, and type aliases is however not mangled.

- The name of imported modules, e.g., `__spam` in `import __spam`. If the module is part of a package (i.e., its name contains a dot), the name is not mangled, e.g., the `__foo` in `import __foo.bar` is not mangled.

- The name of an imported member, e.g., `__f` in `from spam import __f`.

The transformation rule is defined as follows:

- The class name, with leading underscores removed and a single leading underscore inserted, is inserted in front of the identifier, e.g., the identifier `__spam` occurring in a class named `Foo`, `_Foo` or `__Foo` is transformed to `_Foo__spam`.

- If the class name consists only of underscores, the transformation is the identity, e.g., the identifier `__spam` occurring in a class named `_` or `__` is left as is.

### 6.2.2. Літерали

Python підтримує рядкові та байтові літерали та різні числові літерали:

    literal ::=  stringliteral | bytesliteral
                 | integer | floatnumber | imagnumber

Evaluation of a literal yields an object of the given type (string, bytes, integer, floating-point number, complex number) with the given value. The value may be approximated in the case of floating-point and imaginary (complex) literals. See section Літерали for details.

Усі літерали відповідають незмінним типам даних, і, отже, ідентичність об’єкта менш важлива, ніж його значення. Кілька обчислень літералів з однаковим значенням (або те саме входження в текст програми, або інше входження) можуть отримати той самий об’єкт або інший об’єкт з тим самим значенням.

### 6.2.3. Форми в дужках

Форма в дужках – це необов’язковий список виразів, укладений у дужки:

    parenth_form ::=  "(" [starred_expression] ")"

Список виразів у дужках дає все, що дає цей список виразів: якщо список містить принаймні одну кому, він дає кортеж; інакше він дає єдиний вираз, який складає список виразів.

Порожня пара круглих дужок дає порожній об’єкт кортежу. Оскільки кортежі є незмінними, застосовуються ті ж правила, що й для літералів (тобто два входження порожнього кортежу можуть або не можуть давати той самий об’єкт).

Note that tuples are not formed by the parentheses, but rather by use of the comma. The exception is the empty tuple, for which parentheses are required — allowing unparenthesized «nothing» in expressions would cause ambiguities and allow common typos to pass uncaught.

### 6.2.4. Відображення списків, наборів і словників

Для побудови списку, набору або словника Python надає спеціальний синтаксис, званий «дисплеями», кожен з яких у двох варіантах:

- або вміст контейнера перераховано явно, або

- вони обчислюються за допомогою набору інструкцій циклу та фільтрації, які називаються comprehension.

Загальні синтаксичні елементи для розуміння:

    comprehension ::=  assignment_expression comp_for
    comp_for      ::=  ["async"] "for" target_list "in" or_test [comp_iter]
    comp_iter     ::=  comp_for | comp_if
    comp_if       ::=  "if" or_test [comp_iter]

Розуміння складається з одного виразу, за яким слідує принаймні одна пропозиція `for` і нуль або більше пропозицій `for` або `if`. У цьому випадку елементи нового контейнера — це ті, які були б створені шляхом розгляду кожного з пропозицій `for` або `if` блоку, вкладення зліва направо та оцінювання виразу створювати елемент кожного разу, коли досягнуто внутрішнього блоку.

Однак, окрім ітераційного виразу в крайньому лівому реченні `for`, розуміння виконується в окремій неявно вкладеній області. Це гарантує, що імена, призначені в цільовому списку, не «просочуються» в охоплюючу область.

Ітераційний вираз у крайньому лівому реченні `for` обчислюється безпосередньо в охоплюючій області, а потім передається як аргумент до неявно вкладеної області. Наступні пропозиції `for` і будь-яка умова фільтра в крайньому лівому пункті `for` не можуть бути оцінені в охоплюючій області, оскільки вони можуть залежати від значень, отриманих від крайнього лівого ітератора. Наприклад: `[x*y для x в діапазоні (10) для y в діапазоні (x, x+10)]`.

Щоб гарантувати, що розуміння завжди призводить до контейнера відповідного типу, вирази `yield` і `yield from` заборонені в неявно вкладеній області.

Since Python 3.6, in an `async def` function, an `async for` clause may be used to iterate over a asynchronous iterator. A comprehension in an `async def` function may consist of either a `for` or `async for` clause following the leading expression, may contain additional `for` or `async for` clauses, and may also use `await` expressions.

If a comprehension contains `async for` clauses, or if it contains `await` expressions or other asynchronous comprehensions anywhere except the iterable expression in the leftmost `for` clause, it is called an asynchronous comprehension. An asynchronous comprehension may suspend the execution of the coroutine function in which it appears. See also PEP 530.

Added in version 3.6: Були введені асинхронні розуміння.

Змінено в версії 3.8: `yield` і `yield from` заборонені в неявно вкладеній області.

Змінено в версії 3.11: Asynchronous comprehensions are now allowed inside comprehensions in asynchronous functions. Outer comprehensions implicitly become asynchronous.

### 6.2.5. Відображається список

Відображення списку – це, можливо, порожня серія виразів, укладених у квадратні дужки:

    list_display ::=  "[" [flexible_expression_list | comprehension] "]"

Відображення списку дає новий об’єкт списку, вміст якого визначається або списком виразів, або розумінням. Коли надається список виразів, розділених комами, його елементи обчислюються зліва направо та розміщуються в об’єкті списку в такому порядку. Коли надається розуміння, список складається з елементів, отриманих у результаті розуміння.

### 6.2.6. Встановити дисплеї

Відображення набору позначається фігурними дужками та відрізняється від відображення словника відсутністю двокрапки, що розділяє ключі та значення:

    set_display ::=  "{" (flexible_expression_list | comprehension) "}"

Відображення набору дає новий змінний об’єкт набору, вміст якого визначається або послідовністю виразів, або розумінням. Коли надається список виразів, розділених комами, його елементи обчислюються зліва направо та додаються до набору об’єктів. Коли надається розуміння, набір будується з елементів, отриманих у результаті розуміння.

Порожній набір не можна створити за допомогою `{}`; цей літерал створює порожній словник.

### 6.2.7. Відображення словника

A dictionary display is a possibly empty series of dict items (key/value pairs) enclosed in curly braces:

    dict_display       ::=  "{" [dict_item_list | dict_comprehension] "}"
    dict_item_list     ::=  dict_item ("," dict_item)* [","]
    dict_item          ::=  expression ":" expression | "**" or_expr
    dict_comprehension ::=  expression ":" expression comp_for

Відображення словника дає новий об’єкт словника.

If a comma-separated sequence of dict items is given, they are evaluated from left to right to define the entries of the dictionary: each key object is used as a key into the dictionary to store the corresponding value. This means that you can specify the same key multiple times in the dict item list, and the final dictionary’s value for that key will be the last one given.

A double asterisk `**` denotes dictionary unpacking. Its operand must be a mapping. Each mapping item is added to the new dictionary. Later values replace values already set by earlier dict items and earlier dictionary unpackings.

Added in version 3.5: Розпакування у словникові відображення, спочатку запропоноване PEP 448.

Розуміння dict, на відміну від списків і набору, потребує двох виразів, розділених двокрапкою, за якими слідують звичайні пропозиції «for» і «if». Коли виконується розуміння, отримані елементи ключа та значення вставляються в новий словник у тому порядку, в якому вони створені.

Restrictions on the types of the key values are listed earlier in section Стандартна ієрархія типів. (To summarize, the key type should be hashable, which excludes all mutable objects.) Clashes between duplicate keys are not detected; the last value (textually rightmost in the display) stored for a given key value prevails.

Змінено в версії 3.8: До Python 3.8 у розуміннях dict порядок оцінки ключа та значення не був чітко визначений. У CPython значення було обчислено перед ключем. Починаючи з 3.8, ключ оцінюється перед значенням, як запропоновано PEP 572.

### 6.2.8. Генератор виразів

Генеруючий вираз — це компактний генераторний запис у круглих дужках:

    generator_expression ::=  "(" expression comp_for ")"

Генеруючий вираз дає новий генераторний об’єкт. Його синтаксис такий самий, як і для розуміння, за винятком того, що він узятий у дужки замість дужок або фігурних дужок.

Змінні, які використовуються у виразі генератора, обчислюються ліниво, коли метод `__next__()` викликається для об’єкта генератора (так само, як і звичайні генератори). Однак ітераційний вираз у крайньому лівому реченні `for` негайно обчислюється, тому помилка, створена ним, буде видана в точці, де визначено вираз генератора, а не в точці, де перше значення відновлено. Наступні пропозиції `for` і будь-яка умова фільтра в крайньому лівому пункті `for` не можуть бути оцінені в охоплюючій області, оскільки вони можуть залежати від значень, отриманих від крайнього лівого ітератора. Наприклад: `(x*y для x в діапазоні (10) для y в діапазоні (x, x+10))`.

У викликах лише з одним аргументом дужки можна опускати. Подробиці див. у розділі Дзвінки.

Щоб уникнути перешкоджання очікуваній роботі самого виразу генератора, вирази `yield` і `yield from` заборонені в неявно визначеному генераторі.

Якщо вираз генератора містить пропозиції `async for` або вирази `await`, це називається asynchronous generator expression. Вираз асинхронного генератора повертає новий об’єкт асинхронного генератора, який є асинхронним ітератором (див. Асинхронні ітератори).

Added in version 3.6: Було введено асинхронні генераторні вирази.

Змінено в версії 3.7: До Python 3.7 вирази асинхронного генератора могли з’являтися лише в співпрограмах `async def`. Починаючи з 3.7, будь-яка функція може використовувати вирази асинхронного генератора.

Змінено в версії 3.8: `yield` і `yield from` заборонені в неявно вкладеній області.

### 6.2.9. Вирази дохідності

    yield_atom       ::=  "(" yield_expression ")"
    yield_from       ::=  "yield" "from" expression
    yield_expression ::=  "yield" yield_list | yield_from

Вираз yield використовується під час визначення функції generator або функції asynchronous generator і тому може використовуватися лише в тілі визначення функції. Використання виразу yield у тілі функції робить цю функцію функцією-генератором, а використання його в тілі функції `async def` призводить до того, що функція співпрограми стає асинхронною функцією-генератором. Наприклад:

    def gen():  # defines a generator function
        yield 123

    async def agen(): # defines an asynchronous generator function
        yield 123

Через їхній побічний вплив на область, що містить, вирази `yield` не дозволені як частина неявно визначених областей, які використовуються для реалізації розуміння та виразів генератора.

Змінено в версії 3.8: Вирази yield, заборонені в неявно вкладених областях, що використовуються для реалізації виразів розуміння та генератора.

Функції генератора описані нижче, тоді як функції асинхронного генератора описані окремо в розділі Функції асинхронного генератора.

When a generator function is called, it returns an iterator known as a generator. That generator then controls the execution of the generator function. The execution starts when one of the generator’s methods is called. At that time, the execution proceeds to the first yield expression, where it is suspended again, returning the value of `yield_list` to the generator’s caller, or `None` if `yield_list` is omitted. By suspended, we mean that all local state is retained, including the current bindings of local variables, the instruction pointer, the internal evaluation stack, and the state of any exception handling. When the execution is resumed by calling one of the generator’s methods, the function can proceed exactly as if the yield expression were just another external call. The value of the yield expression after resuming depends on the method which resumed the execution. If `__next__()` is used (typically via either a `for` or the `next()` builtin) then the result is `None`. Otherwise, if `send()` is used, then the result will be the value passed in to that method.

Усе це робить функції генератора досить схожими на співпрограми; вони поступаються кілька разів, вони мають більше однієї точки входу, і їхнє виконання може бути призупинено. Єдина відмінність полягає в тому, що функція-генератор не може контролювати, де має продовжуватися виконання після того, як вона виходить; керування завжди передається абоненту генератора.

Вирази yield дозволені будь-де в конструкції `try`. Якщо генератор не відновлено до його завершення (досягнувши нульової кількості посилань або збираючи сміття), буде викликано метод `close()` генератора-ітератора, дозволяючи будь-які очікуючі `finally` пропозиції для виконання.

Коли використовується `yield from <expr>`, наданий вираз має бути повторюваним. Значення, отримані шляхом ітерації цього ітерованого, передаються безпосередньо до виклику методів поточного генератора. Будь-які значення, передані за допомогою `send()`, і будь-які винятки, передані за допомогою `throw()`, передаються базовому ітератору, якщо він має відповідні методи. Якщо це не так, то `send()` викличе `AttributeError` або `TypeError`, а `throw()` просто викличе переданий виняток негайно.

Коли основний ітератор завершено, атрибут `value` піднятого екземпляра `StopIteration` стає значенням виразу yield. Його можна встановити явно під час виклику `StopIteration` або автоматично, коли субітератор є генератором (шляхом повернення значення з субгенератора).

Змінено в версії 3.3: Додано `yield from <expr>` для делегування потоку керування субітератору.

Дужки можуть бути опущені, якщо вираз yield є єдиним виразом у правій частині оператора призначення.

Дивись також

PEP 255 - Прості генератори

  Пропозиція щодо додавання генераторів і оператора `yield` до Python.

PEP 342 - Співпрограми через розширені генератори

  Пропозиція покращити API та синтаксис генераторів, зробивши їх придатними для використання як простих співпрограм.

PEP 380 - Синтаксис для делегування підгенератору

  Пропозиція запровадити синтаксис `yield_from`, що спрощує делегування субгенераторам.

PEP 525 - Асинхронні генератори

  Пропозиція, яка розширила PEP 492 шляхом додавання можливостей генератора до функцій співпрограми.

#### 6.2.9.1. Методи генератор-ітератор

У цьому підрозділі описано методи ітератора генератора. Вони можуть використовуватися для керування виконанням функції генератора.

Зауважте, що виклик будь-якого з наведених нижче методів генератора, коли генератор уже виконується, викликає виняткову ситуацію `ValueError`.

generator.__next__()

  Starts the execution of a generator function or resumes it at the last executed yield expression. When a generator function is resumed with a `__next__()` method, the current yield expression always evaluates to `None`. The execution then continues to the next yield expression, where the generator is suspended again, and the value of the `yield_list` is returned to `__next__()`“s caller. If the generator exits without yielding another value, a `StopIteration` exception is raised.

  Цей метод зазвичай викликається неявно, напр. за допомогою циклу `for` або за допомогою вбудованої функції `next()`.

generator.send(value)

  Відновлює виконання та «надсилає» значення у функцію генератора. Аргумент value стає результатом поточного виразу yield. Метод `send()` повертає наступне значення, отримане генератором, або викликає `StopIteration`, якщо генератор завершує роботу, не видаючи іншого значення. Коли `send()` викликається для запуску генератора, його потрібно викликати з `None` як аргументом, оскільки немає виразу yield, який міг би отримати значення.

generator.throw(value)
generator.throw(type[, value[, traceback]])

  Викликає виняток у точці, де генератор було призупинено, і повертає наступне значення, отримане функцією генератора. Якщо генератор завершує роботу, не видаючи іншого значення, виникає виняток `StopIteration`. Якщо функція генератора не перехоплює переданий виняток або викликає інший виняток, тоді цей виняток поширюється на виклик.

  У типовому використанні це викликається з одним винятком, подібним до того, як використовується ключове слово `raise`.

  For backwards compatibility, however, the second signature is supported, following a convention from older versions of Python. The type argument should be an exception class, and value should be an exception instance. If the value is not provided, the type constructor is called to get an instance. If traceback is provided, it is set on the exception, otherwise any existing `__traceback__` attribute stored in value may be cleared.

  Змінено в версії 3.12: The second signature (type[, value[, traceback]]) is deprecated and may be removed in a future version of Python.

generator.close()

  Raises a `GeneratorExit` at the point where the generator function was paused. If the generator function catches the exception and returns a value, this value is returned from `close()`. If the generator function is already closed, or raises `GeneratorExit` (by not catching the exception), `close()` returns `None`. If the generator yields a value, a `RuntimeError` is raised. If the generator raises any other exception, it is propagated to the caller. If the generator has already exited due to an exception or normal exit, `close()` returns `None` and has no other effect.

  Змінено в версії 3.13: If a generator returns a value upon being closed, the value is returned by `close()`.

#### 6.2.9.2. Приклади

Ось простий приклад, який демонструє поведінку генераторів і функцій генератора:

    >>> def echo(value=None):
    ...     print("Execution starts when 'next()' is called for the first time.")
    ...     try:
    ...         while True:
    ...             try:
    ...                 value = (yield value)
    ...             except Exception as e:
    ...                 value = e
    ...     finally:
    ...         print("Don't forget to clean up when 'close()' is called.")
    ...
    >>> generator = echo(1)
    >>> print(next(generator))
    Execution starts when 'next()' is called for the first time.
    1
    >>> print(next(generator))
    None
    >>> print(generator.send(2))
    2
    >>> generator.throw(TypeError, "spam")
    TypeError('spam',)
    >>> generator.close()
    Don't forget to clean up when 'close()' is called.

Приклади використання `yield from` див. PEP 380: Синтаксис для делегування субгенератору у розділі «Що нового в Python».

#### 6.2.9.3. Функції асинхронного генератора

Наявність виразу yield у функції чи методі, визначеному за допомогою `async def`, далі визначає функцію як функцію asynchronous generator.

Коли викликається функція асинхронного генератора, вона повертає асинхронний ітератор, відомий як об’єкт асинхронного генератора. Потім цей об’єкт керує виконанням функції генератора. Асинхронний об’єкт генератора зазвичай використовується в операторі `async for` у функції співпрограми аналогічно тому, як об’єкт генератора використовувався б у операторі `for`.

Calling one of the asynchronous generator’s methods returns an awaitable object, and the execution starts when this object is awaited on. At that time, the execution proceeds to the first yield expression, where it is suspended again, returning the value of `yield_list` to the awaiting coroutine. As with a generator, suspension means that all local state is retained, including the current bindings of local variables, the instruction pointer, the internal evaluation stack, and the state of any exception handling. When the execution is resumed by awaiting on the next object returned by the asynchronous generator’s methods, the function can proceed exactly as if the yield expression were just another external call. The value of the yield expression after resuming depends on the method which resumed the execution. If `__anext__()` is used then the result is `None`. Otherwise, if `asend()` is used, then the result will be the value passed in to that method.

Якщо асинхронний генератор завершує роботу раніше через `break`, скасування завдання виклику або інші винятки, запуститься асинхронний код очищення генератора та, можливо, викличе винятки або отримає доступ до змінних контексту в неочікуваному контексті — можливо, після час життя завдань залежить від цього, або під час завершення циклу подій, коли викликається хук збирання сміття асинхронного генератора. Щоб запобігти цьому, абонент повинен явно закрити асинхронний генератор, викликавши метод `aclose()`, щоб завершити генератор і остаточно від’єднати його від циклу подій.

У функції асинхронного генератора вирази yield дозволені будь-де в конструкції `try`. Однак, якщо асинхронний генератор не відновлено до його завершення (досягнувши нульового підрахунку посилань або збираючи сміття), тоді вираз yield у конструкції `try` може призвести до збою виконання очікуваного `finally`. У цьому випадку цикл подій або планувальник, який запускає асинхронний генератор, відповідає за виклик методу `aclose()` асинхронного генератора-ітератора та запуск отриманого об’єкта співпрограми, таким чином дозволяючи будь-які очікуючі `finally` для виконання.

Щоб подбати про фіналізацію після завершення циклу подій, цикл подій має визначати функцію finalizer, яка приймає асинхронний генератор-ітератор і, ймовірно, викликає `aclose()` і виконує співпрограму. Цей фіналізатор можна зареєструвати, викликавши `sys.set_asyncgen_hooks()`. Під час першого повторення асинхронний генератор-ітератор зберігатиме зареєстрований фіналізатор, який буде викликаний під час фіналізації. Для довідкового прикладу методу finalizer перегляньте реалізацію `asyncio.Loop.shutdown_asyncgens` у Lib/asyncio/base_events.py.

Вираз `yield from <expr>` є синтаксичною помилкою під час використання у функції асинхронного генератора.

#### 6.2.9.4. Методи асинхронного генератора-ітератора

У цьому підрозділі описано методи ітератора асинхронного генератора, які використовуються для керування виконанням функції генератора.

coroutine agen.__anext__()

  Returns an awaitable which when run starts to execute the asynchronous generator or resumes it at the last executed yield expression. When an asynchronous generator function is resumed with an `__anext__()` method, the current yield expression always evaluates to `None` in the returned awaitable, which when run will continue to the next yield expression. The value of the `yield_list` of the yield expression is the value of the `StopIteration` exception raised by the completing coroutine. If the asynchronous generator exits without yielding another value, the awaitable instead raises a `StopAsyncIteration` exception, signalling that the asynchronous iteration has completed.

  Цей метод зазвичай викликається неявно циклом `async for`.

coroutine agen.asend(value)

  Returns an awaitable which when run resumes the execution of the asynchronous generator. As with the `send()` method for a generator, this «sends» a value into the asynchronous generator function, and the value argument becomes the result of the current yield expression. The awaitable returned by the `asend()` method will return the next value yielded by the generator as the value of the raised `StopIteration`, or raises `StopAsyncIteration` if the asynchronous generator exits without yielding another value. When `asend()` is called to start the asynchronous generator, it must be called with `None` as the argument, because there is no yield expression that could receive the value.

coroutine agen.athrow(value)
coroutine agen.athrow(type[, value[, traceback]])

  Повертає awaitable, який викликає виняток типу `type` у точці, де асинхронний генератор було призупинено, і повертає наступне значення, отримане функцією генератора як значення викликаного винятку `StopIteration`. Якщо асинхронний генератор завершує роботу, не видаючи іншого значення, очікуваний виклик викликає виняток `StopAsyncIteration`. Якщо функція генератора не перехоплює переданий виняток або викликає інший виняток, тоді, коли виконується очікуваний, цей виняток поширюється на виклик очікуваного.

  Змінено в версії 3.12: The second signature (type[, value[, traceback]]) is deprecated and may be removed in a future version of Python.

coroutine agen.aclose()

  Повертає awaitable, який під час виконання видає `GeneratorExit` у функцію асинхронного генератора в точці, де її було призупинено. Якщо функція асинхронного генератора завершує роботу належним чином, уже закрита або викликає `GeneratorExit` (не перехоплюючи виняток), тоді повернутий awaitable викличе виняток `StopIteration`. Будь-які подальші очікування, повернуті наступними викликами асинхронного генератора, викличуть виняток `StopAsyncIteration`. Якщо асинхронний генератор видає значення, awaitable викликає `RuntimeError`. Якщо асинхронний генератор викликає будь-який інший виняток, він поширюється на виклик очікуваного. Якщо асинхронний генератор уже завершив роботу через виняток або звичайний вихід, тоді подальші виклики `aclose()` повернуть очікуваний, який нічого не робить.

## 6.3. Праймеріз

Основні представляють найбільш тісно зв’язані операції мови. Їх синтаксис:

    primary ::=  atom | attributeref | subscription | slicing | call

### 6.3.1. Посилання на атрибути

Посилання на атрибут є основним, за яким йдуть крапка та ім’я:

    attributeref ::=  primary "." identifier

The primary must evaluate to an object of a type that supports attribute references, which most objects do. This object is then asked to produce the attribute whose name is the identifier. The type and value produced is determined by the object. Multiple evaluations of the same attribute reference may yield different objects.

This production can be customized by overriding the `__getattribute__()` method or the `__getattr__()` method. The `__getattribute__()` method is called first and either returns a value or raises `AttributeError` if the attribute is not available.

If an `AttributeError` is raised and the object has a `__getattr__()` method, that method is called as a fallback.

### 6.3.2. Підписки

Підписка екземпляра класу контейнера зазвичай вибирає елемент із контейнера. Підписка загального класу зазвичай повертатиме об’єкт GenericAlias.

    subscription ::=  primary "[" flexible_expression_list "]"

Коли об’єкт має індекс, інтерпретатор обчислить основний і список виразів.

Основний має обчислювати об’єкт, який підтримує підписку. Об’єкт може підтримувати підписку через визначення одного або обох `__getitem__()` і `__class_getitem__()`. Коли основний має індекс, обчислений результат списку виразів буде передано одному з цих методів. Щоб дізнатися більше про те, коли `__class_getitem__` викликається замість `__getitem__`, перегляньте __class_getitem__ проти __getitem__.

If the expression list contains at least one comma, or if any of the expressions are starred, the expression list will evaluate to a `tuple` containing the items of the expression list. Otherwise, the expression list will evaluate to the value of the list’s sole member.

Змінено в версії 3.11: Expressions in an expression list may be starred. See PEP 646.

Для вбудованих об’єктів є два типи об’єктів, які підтримують підписку через `__getitem__()`:

1. Відображення. Якщо основним є mapping, список виразів має обчислювати об’єкт, значення якого є одним із ключів відображення, а підписка вибирає значення у відображенні, яке відповідає цьому ключу. Прикладом вбудованого класу відображення є клас `dict`.

2. Послідовності. Якщо основним є sequence, список виразів має обчислюватися як `int` або `slice` (як описано в наступному розділі). Приклади вбудованих класів послідовності включають класи `str`, `list` і `tuple`.

The formal syntax makes no special provision for negative indices in sequences. However, built-in sequences all provide a `__getitem__()` method that interprets negative indices by adding the length of the sequence to the index so that, for example, `x[-1]` selects the last item of `x`. The resulting value must be a nonnegative integer less than the number of items in the sequence, and the subscription selects the item whose index is that value (counting from zero). Since the support for negative indices and slicing occurs in the object’s `__getitem__()` method, subclasses overriding this method will need to explicitly add that support.

`string` — це особливий вид послідовності, елементами якої є символи. Символ — це не окремий тип даних, а рядок із рівно одного символу.

### 6.3.3. Нарізки

Нарізка вибирає діапазон елементів в об’єкті послідовності (наприклад, рядок, кортеж або список). Зрізи можуть використовуватися як вирази або як цілі в операторах призначення або `del`. Синтаксис нарізки:

    slicing      ::=  primary "[" slice_list "]"
    slice_list   ::=  slice_item ("," slice_item)* [","]
    slice_item   ::=  expression | proper_slice
    proper_slice ::=  [lower_bound] ":" [upper_bound] [ ":" [stride] ]
    lower_bound  ::=  expression
    upper_bound  ::=  expression
    stride       ::=  expression

Тут існує неоднозначність у формальному синтаксисі: все, що виглядає як список виразів, також виглядає як список фрагментів, тому будь-яку підписку можна інтерпретувати як фрагмент. Замість подальшого ускладнення синтаксису, це усувається визначенням того, що в цьому випадку інтерпретація як підписка має пріоритет над інтерпретацією як нарізка (це випадок, якщо список зрізів не містить належного зрізу).

The semantics for a slicing are as follows. The primary is indexed (using the same `__getitem__()` method as normal subscription) with a key that is constructed from the slice list, as follows. If the slice list contains at least one comma, the key is a tuple containing the conversion of the slice items; otherwise, the conversion of the lone slice item is the key. The conversion of a slice item that is an expression is that expression. The conversion of a proper slice is a slice object (see section Стандартна ієрархія типів) whose `start`, `stop` and `step` attributes are the values of the expressions given as lower bound, upper bound and stride, respectively, substituting `None` for missing expressions.

### 6.3.4. Дзвінки

Виклик викликає об’єкт, який можна викликати (наприклад, function) з можливо порожньою серією аргументів:

    call                 ::=  primary "(" [argument_list [","] | comprehension] ")"
    argument_list        ::=  positional_arguments ["," starred_and_keywords]
                                ["," keywords_arguments]
                              | starred_and_keywords ["," keywords_arguments]
                              | keywords_arguments
    positional_arguments ::=  positional_item ("," positional_item)*
    positional_item      ::=  assignment_expression | "*" expression
    starred_and_keywords ::=  ("*" expression | keyword_item)
                              ("," "*" expression | "," keyword_item)*
    keywords_arguments   ::=  (keyword_item | "**" expression)
                              ("," keyword_item | "," "**" expression)*
    keyword_item         ::=  identifier "=" expression

Необов’язкова кінцева кома може бути присутнім після позиційних і ключових аргументів, але не впливає на семантику.

The primary must evaluate to a callable object (user-defined functions, built-in functions, methods of built-in objects, class objects, methods of class instances, and all objects having a `__call__()` method are callable). All argument expressions are evaluated before the call is attempted. Please refer to section Визначення функцій for the syntax of formal parameter lists.

If keyword arguments are present, they are first converted to positional arguments, as follows. First, a list of unfilled slots is created for the formal parameters. If there are N positional arguments, they are placed in the first N slots. Next, for each keyword argument, the identifier is used to determine the corresponding slot (if the identifier is the same as the first formal parameter name, the first slot is used, and so on). If the slot is already filled, a `TypeError` exception is raised. Otherwise, the argument is placed in the slot, filling it (even if the expression is `None`, it fills the slot). When all arguments have been processed, the slots that are still unfilled are filled with the corresponding default value from the function definition. (Default values are calculated, once, when the function is defined; thus, a mutable object such as a list or dictionary used as default value will be shared by all calls that don’t specify an argument value for the corresponding slot; this should usually be avoided.) If there are any unfilled slots for which no default value is specified, a `TypeError` exception is raised. Otherwise, the list of filled slots is used as the argument list for the call.

Деталі реалізації CPython: Реалізація може надавати вбудовані функції, чиї позиційні параметри не мають імен, навіть якщо вони «іменовані» з метою документації, і які, отже, не можуть бути надані за ключовими словами. У CPython це стосується функцій, реалізованих у C, які використовують `PyArg_ParseTuple()` для аналізу своїх аргументів.

Якщо позиційних аргументів більше, ніж слотів формальних параметрів, виникає виняток `TypeError`, якщо не існує формального параметра, що використовує синтаксис `*identifier`; у цьому випадку формальний параметр отримує кортеж, що містить зайві позиційні аргументи (або порожній кортеж, якщо надлишкових позиційних аргументів не було).

Якщо будь-який аргумент ключового слова не відповідає офіційній назві параметра, виникає виняток `TypeError`, якщо не існує формального параметра, що використовує синтаксис `**ідентифікатор`; у цьому випадку формальний параметр отримує словник, що містить надлишкові аргументи ключового слова (з використанням ключових слів як ключів і значень аргументів як відповідних значень), або (новий) порожній словник, якщо не було надлишкових аргументів ключового слова.

Якщо у виклику функції з’являється синтаксис `*expression`, `expression` має обчислюватися як iterable. Елементи з цих ітерованих елементів розглядаються як додаткові позиційні аргументи. Для виклику `f(x1, x2, *y, x3, x4)`, якщо y обчислюється як послідовність y1, …, yM, це еквівалентно виклику з M+ 4 позиційні аргументи x1, x2, y1, …, yM, x3, x4.

Наслідком цього є те, що хоча синтаксис `*виразу` може з’явитися після явних аргументів ключового слова, він обробляється перед аргументами ключового слова (та будь-якими аргументами `**виразу` – див. нижче). Тому:

    >>> def f(a, b):
    ...     print(a, b)
    ...
    >>> f(b=1, *(2,))
    2 1
    >>> f(a=1, *(2,))
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
    TypeError: f() got multiple values for keyword argument 'a'
    >>> f(1, *(2,))
    1 2

It is unusual for both keyword arguments and the `*expression` syntax to be used in the same call, so in practice this confusion does not often arise.

If the syntax `**expression` appears in the function call, `expression` must evaluate to a mapping, the contents of which are treated as additional keyword arguments. If a parameter matching a key has already been given a value (by an explicit keyword argument, or from another unpacking), a `TypeError` exception is raised.

When `**expression` is used, each key in this mapping must be a string. Each value from the mapping is assigned to the first formal parameter eligible for keyword assignment whose name is equal to the key. A key need not be a Python identifier (e.g. `"max-temp °F"` is acceptable, although it will not match any formal parameter that could be declared). If there is no match to a formal parameter the key-value pair is collected by the `**` parameter, if there is one, or if there is not, a `TypeError` exception is raised.

Формальні параметри, що використовують синтаксис `*ідентифікатор` або `**ідентифікатор`, не можуть використовуватися як слоти позиційних аргументів або як імена аргументів ключових слів.

Змінено в версії 3.5: Виклики функцій приймають будь-яку кількість розпакувань `*` і `**`, позиційні аргументи можуть слідувати за ітерованими розпакуваннями (`*`), а аргументи ключових слів можуть слідувати за розпакуваннями словника (`**`). Спочатку запропоновано PEP 448.

Виклик завжди повертає певне значення, можливо, `None`, якщо тільки це не викликає виняткову ситуацію. Спосіб обчислення цього значення залежить від типу викликаного об’єкта.

Якщо це—

функція, визначена користувачем:

  Блок коду для функції виконується, передаючи їй список аргументів. Перше, що зробить блок коду, це прив’яже формальні параметри до аргументів; це описано в розділі Визначення функцій. Коли блок коду виконує оператор `return`, це визначає значення, що повертається викликом функції.

вбудована функція або метод:

  Результат залежить від перекладача; див. Вбудовані функції для опису вбудованих функцій і методів.

об’єкт класу:

  Повертається новий екземпляр цього класу.

метод екземпляра класу:

  Викликається відповідна функція, визначена користувачем, зі списком аргументів, який на один довший за список аргументів виклику: екземпляр стає першим аргументом.

екземпляр класу:

  The class must define a `__call__()` method; the effect is then the same as if that method was called.

## 6.4. Очікуйте вираження

Призупинити виконання coroutine на об’єкті awaitable. Можна використовувати лише всередині функції співпрограми (coroutine function).

    await_expr ::=  "await" primary

Added in version 3.5.

## 6.5. Оператор енергетики

Потужний оператор прив’язується сильніше, ніж унарні оператори зліва; він зв’язується менш тісно, ніж унарні оператори справа. Синтаксис:

    power ::=  (await_expr | primary) ["**" u_expr]

Таким чином, у послідовності степеневих і унарних операторів без дужок оператори обчислюються справа наліво (це не обмежує порядок обчислення для операндів): `-1**2` призводить до `-1` .

Оператор ступеня має таку саму семантику, як і вбудована функція `pow()`, коли викликається з двома аргументами: він повертає свій лівий аргумент, зведений до степеня правого аргументу. Числові аргументи спочатку перетворюються на загальний тип, і результат має відповідний тип.

Для операндів int результат має той самий тип, що й операнди, якщо другий аргумент не є від’ємним; у цьому випадку всі аргументи перетворюються на значення float і видає результат float. Наприклад, `10**2` повертає `100`, а `10**-2` повертає `0,01`.

Піднесення `0.0` до негативного степеня призводить до `ZeroDivisionError`. Зведення від’ємного числа до дробового степеня призводить до `complex` числа. (У попередніх версіях це викликало `ValueError`.)

This operation can be customized using the special `__pow__()` and `__rpow__()` methods.

## 6.6. Унарні арифметичні та порозрядні операції

Усі унарні арифметичні та порозрядні операції мають однаковий пріоритет:

    u_expr ::=  power | "-" u_expr | "+" u_expr | "~" u_expr

The unary `-` (minus) operator yields the negation of its numeric argument; the operation can be overridden with the `__neg__()` special method.

The unary `+` (plus) operator yields its numeric argument unchanged; the operation can be overridden with the `__pos__()` special method.

The unary `~` (invert) operator yields the bitwise inversion of its integer argument. The bitwise inversion of `x` is defined as `-(x+1)`. It only applies to integral numbers or to custom objects that override the `__invert__()` special method.

В усіх трьох випадках, якщо аргумент не має належного типу, виникає виняток `TypeError`.

## 6.7. Двійкові арифметичні операції

Двійкові арифметичні операції мають загальноприйняті рівні пріоритету. Зверніть увагу, що деякі з цих операцій також застосовуються до певних нечислових типів. Окрім оператора степеня, існує лише два рівні: один для мультиплікативних операторів і один для адитивних операторів:

    m_expr ::=  u_expr | m_expr "*" u_expr | m_expr "@" m_expr |
                m_expr "//" u_expr | m_expr "/" u_expr |
                m_expr "%" u_expr
    a_expr ::=  m_expr | a_expr "+" m_expr | a_expr "-" m_expr

Оператор `*` (множення) повертає добуток своїх аргументів. Обидва аргументи мають бути числами, або один аргумент має бути цілим числом, а інший — послідовністю. У першому випадку числа перетворюються на загальний тип, а потім перемножуються. В останньому випадку виконується повторення послідовності; негативний коефіцієнт повторення дає порожню послідовність.

This operation can be customized using the special `__mul__()` and `__rmul__()` methods.

Оператор `@` (at) призначений для використання для множення матриці. Жодні вбудовані типи Python не реалізують цей оператор.

This operation can be customized using the special `__matmul__()` and `__rmatmul__()` methods.

Added in version 3.5.

Оператори `/` (поділ) і `//` (поділ на поверх) видають приватне своїх аргументів. Числові аргументи спочатку перетворюються на загальний тип. Ділення цілих чисел дає значення з плаваючою точкою, а поділення цілих чисел дає ціле число; результатом є математичне ділення із застосованою до результату функцією «підлога». Ділення на нуль викликає виключення `ZeroDivisionError`.

The division operation can be customized using the special `__truediv__()` and `__rtruediv__()` methods. The floor division operation can be customized using the special `__floordiv__()` and `__rfloordiv__()` methods.

The `%` (modulo) operator yields the remainder from the division of the first argument by the second. The numeric arguments are first converted to a common type. A zero right argument raises the `ZeroDivisionError` exception. The arguments may be floating-point numbers, e.g., `3.14%0.7` equals `0.34` (since `3.14` equals `4*0.7 + 0.34`.) The modulo operator always yields a result with the same sign as its second operand (or zero); the absolute value of the result is strictly smaller than the absolute value of the second operand [1].

Оператори поділу поверху та модульні оператори з’єднані такою тотожністю: `x == (x//y)*y + (x%y)`. Поділ на поверх і модуль також пов’язані з вбудованою функцією `divmod()`: `divmod(x, y) == (x//y, x%y)`. [2].

На додаток до виконання операції за модулем над числами, оператор `%` також перевантажується рядковими об’єктами для виконання старого форматування рядків (також відомого як інтерполяція). Синтаксис для форматування рядків описано в Довіднику з бібліотеки Python, розділ Форматування рядків у стилі printf.

The modulo operation can be customized using the special `__mod__()` and `__rmod__()` methods.

The floor division operator, the modulo operator, and the `divmod()` function are not defined for complex numbers. Instead, convert to a floating-point number using the `abs()` function if appropriate.

Оператор `+` (додавання) повертає суму своїх аргументів. Обидва аргументи мають бути числами або обома послідовностями одного типу. У першому випадку числа перетворюються на загальний тип, а потім сумуються. В останньому випадку послідовності об’єднані.

This operation can be customized using the special `__add__()` and `__radd__()` methods.

Оператор `-` (віднімання) повертає різницю своїх аргументів. Числові аргументи спочатку перетворюються на загальний тип.

This operation can be customized using the special `__sub__()` and `__rsub__()` methods.

## 6.8. Змінні операції

Операції зсуву мають нижчий пріоритет, ніж арифметичні операції:

    shift_expr ::=  a_expr | shift_expr ("<<" | ">>") a_expr

Ці оператори приймають цілі числа як аргументи. Вони зсувають перший аргумент вліво або вправо на кількість бітів, задану другим аргументом.

The left shift operation can be customized using the special `__lshift__()` and `__rlshift__()` methods. The right shift operation can be customized using the special `__rshift__()` and `__rrshift__()` methods.

Зсув праворуч на n бітів визначається як нижнє ділення на `pow(2,n)`. Зсув ліворуч на n бітів визначається як множення на `pow(2,n)`.

## 6.9. Бінарні побітові операції

Кожна з трьох побітових операцій має різний рівень пріоритету:

    and_expr ::=  shift_expr | and_expr "&" shift_expr
    xor_expr ::=  and_expr | xor_expr "^" and_expr
    or_expr  ::=  xor_expr | or_expr "|" xor_expr

The `&` operator yields the bitwise AND of its arguments, which must be integers or one of them must be a custom object overriding `__and__()` or `__rand__()` special methods.

The `^` operator yields the bitwise XOR (exclusive OR) of its arguments, which must be integers or one of them must be a custom object overriding `__xor__()` or `__rxor__()` special methods.

The `|` operator yields the bitwise (inclusive) OR of its arguments, which must be integers or one of them must be a custom object overriding `__or__()` or `__ror__()` special methods.

## 6.10. Порівняння

На відміну від C, усі операції порівняння в Python мають однаковий пріоритет, який нижчий, ніж у будь-якої арифметичної операції, операції зсуву чи побітової операції. Крім того, на відміну від C, такі вирази, як `a < b < c`, мають тлумачення, яке є звичайним у математиці:

    comparison    ::=  or_expr (comp_operator or_expr)*
    comp_operator ::=  "<" | ">" | "==" | ">=" | "<=" | "!="
                       | "is" ["not"] | ["not"] "in"

Порівняння дають логічні значення: `True` або `False`. Спеціальні rich comparison methods можуть повертати не логічні значення. У цьому випадку Python викличе `bool()` для такого значення в логічних контекстах.

Порівняння можна довільно об’єднати в ланцюжок, наприклад, `x < y <= z` еквівалентно `x < y і y <= z`, за винятком того, що `y` обчислюється лише один раз (але в обох випадках `z` взагалі не обчислюється, якщо `x < y` виявляється хибним).

Формально, якщо a, b, c, …, y, z є виразами, а op1, op2, …, opN є операторами порівняння, тоді `a op1 b op2 c ... y opN z` еквівалентний `a op1 b і b op2 c і ... y opN z`, за винятком того, що кожен вираз обчислюється щонайбільше один раз.

Зауважте, що `a op1 b op2 c` не передбачає жодного порівняння між a і c, тому, наприклад, `x < y > z` є абсолютно законним (хоча, можливо, не дуже).

### 6.10.1. Порівняння цінностей

Оператори `<`, `>`, `==`, `>=`, `<=` і `!=` порівнюють значення двох об’єктів. Об’єкти не обов’язково мають однаковий тип.

У розділі Об’єкти, значення та типи зазначено, що об’єкти мають значення (крім типу та ідентичності). Значення об’єкта є досить абстрактним поняттям у Python: наприклад, не існує канонічного методу доступу до значення об’єкта. Крім того, немає вимоги, щоб значення об’єкта було сконструйовано певним чином, напр. складається з усіх своїх атрибутів даних. Оператори порівняння реалізують певне уявлення про цінність об’єкта. Можна думати про них як про визначення значення об’єкта опосередковано, за допомогою реалізації порівняння.

Because all types are (direct or indirect) subtypes of `object`, they inherit the default comparison behavior from `object`. Types can customize their comparison behavior by implementing rich comparison methods like `__lt__()`, described in Базове налаштування.

Поведінка за умовчанням для порівняння рівності (`==` і `!=`) базується на ідентичності об’єктів. Отже, порівняння рівності екземплярів з однаковою тотожністю призводить до рівності, а порівняння рівності екземплярів з різними ідентичністями призводить до нерівності. Мотивацією такої поведінки за замовчуванням є бажання, щоб усі об’єкти були рефлексивними (тобто `x є y` означає `x == y`).

Порівняння порядку за замовчуванням (`<`, `>`, `<=`, and `> =`) не надається; спроба викликає `TypeError`. Мотивацією такої поведінки за замовчуванням є відсутність аналогічного інваріанта, як для рівності.

Поведінка порівняння рівності за замовчуванням, тобто екземпляри з різними ідентифікаторами завжди нерівні, може відрізнятися від того, які типи потребуватимуть розумного визначення значення об’єкта та рівності на основі значення. Таким типам потрібно буде налаштувати свою поведінку порівняння, і насправді це зробили кілька вбудованих типів.

У наведеному нижче списку описано поведінку порівняння найважливіших вбудованих типів.

- Числа вбудованих числових типів (Числові типи — int, float, complex) і стандартних бібліотечних типів `fractions.Fraction` і `decimal.Decimal` можна порівнювати всередині та між типами, з обмеженням що комплексні числа не підтримують порівняння порядку. У межах залучених типів вони порівнюють математично (алгоритмічно) правильно без втрати точності.

  Нечислові значення `float('NaN')` і `decimal.Decimal('NaN')` є спеціальними. Будь-яке впорядковане порівняння числа з нечисловим значенням є хибним. Протиінтуїтивний висновок полягає в тому, що нечислові значення не дорівнюють самі собі. Наприклад, якщо `x = float('NaN')`, `3 < x`, `x < 3` і `x == x` є помилковими, тоді як `x ! = x` вірно. Така поведінка відповідає стандарту IEEE 754.

- `None` and `NotImplemented` are singletons. PEP 8 advises that comparisons for singletons should always be done with `is` or `is not`, never the equality operators.

- Двійкові послідовності (екземпляри `bytes` або `bytearray`) можна порівнювати всередині та між типами. Вони порівнюють лексикографічно, використовуючи числові значення своїх елементів.

- Рядки (примірники `str`) порівнюються лексикографічно за допомогою числових кодових точок Unicode (результат вбудованої функції `ord()`) їхніх символів. [3]

  Рядки та двійкові послідовності не можна безпосередньо порівнювати.

- Послідовності (екземпляри `tuple`, `list` або `range`) можна порівнювати лише в межах кожного зі своїх типів, з обмеженням, що діапазони не підтримують порівняння порядку. Порівняння рівності між цими типами призводить до нерівності, а впорядковане порівняння між цими типами викликає `TypeError`.

  Послідовності порівнюють лексикографічно за допомогою порівняння відповідних елементів. Вбудовані контейнери зазвичай припускають, що ідентичні об’єкти рівні самі собі. Це дозволяє їм обійти тести на рівність для ідентичних об’єктів, щоб підвищити продуктивність і зберегти свої внутрішні інваріанти.

  Лексикографічне порівняння між вбудованими колекціями працює таким чином:

  - Щоб дві колекції порівнювалися однаково, вони повинні бути одного типу, мати однакову довжину, і кожна пара відповідних елементів має порівнюватися однаковими (наприклад, `[1,2] == (1,2)` false, оскільки тип не той самий).

  - Колекції, які підтримують порівняння порядку, упорядковуються так само, як і їхні перші нерівні елементи (наприклад, `[1,2,x] <= [1,2,y]` має те саме значення, що `x <= y`). Якщо відповідний елемент не існує, коротша колекція впорядковується першою (наприклад, `[1,2] < [1,2,3]` є істинним).

- Mappings (instances of `dict`) compare equal if and only if they have equal `(key, value)` pairs. Equality comparison of the keys and values enforces reflexivity.

  Порівняння порядку (`<`, `>`, `<=`, and `> =`) викликає `TypeError`.

- Набори (екземпляри `set` або `frozenset`) можна порівнювати всередині та між типами.

  Вони визначають оператори порівняння порядку, щоб означати тести підмножини та надмножини. Ці відносини не визначають загальних порядків (наприклад, дві множини `{1,2}` і `{2,3}` не є рівними, ані підмножини одна одної, ані надмножини одна одної). Відповідно, набори не є відповідними аргументами для функцій, які залежать від загального порядку (наприклад, `min()`, `max()` і `sorted()` дають невизначені результати, якщо ввести список наборів як вхідні дані) .

  Порівняння множин посилює рефлексивність її елементів.

- Більшість інших вбудованих типів не мають реалізованих методів порівняння, тому вони успадковують типову поведінку порівняння.

Визначені користувачем класи, які налаштовують свою поведінку порівняння, повинні дотримуватися деяких правил узгодженості, якщо це можливо:

- Порівняння рівності має бути рефлексивним. Іншими словами, ідентичні об’єкти повинні порівнюватися рівними:

  > `x є y` означає `x == y`

- Порівняння має бути симетричним. Іншими словами, наступні вирази повинні мати однаковий результат:

  > `x == y` і `y == x`

  > `x != y` і `y != x`

  > `x < y` and `y > x`

  > `x <= y` and `y > = x`

- Порівняння має бути транзитивним. Наступні (невичерпні) приклади ілюструють це:

  > `x > y і y > z` передбачає `x > z`

  > `x < y і y <= z` передбачає `x < z`

- Зворотне порівняння має призвести до логічного заперечення. Іншими словами, наступні вирази повинні мати однаковий результат:

  > `x == y` і `не x != y`

  > `x < y` and `not x > = y` (для загального впорядкування)

  > `x > y` і `not x <= y` (для загального порядку)

  Останні два вирази застосовуються до повністю впорядкованих колекцій (наприклад, до послідовностей, але не до наборів чи відображень). Дивіться також декоратор `total_ordering()`.

- Результат `hash()` має відповідати рівності. Рівні об’єкти повинні або мати однакове хеш-значення, або бути позначеними як нехешовані.

Python не забезпечує виконання цих правил узгодженості. Фактично, нечислові значення є прикладом недотримання цих правил.

### 6.10.2. Тестові операції членства

Оператори `in` і `not in` перевіряють членство. `x in s` обчислюється як `True`, якщо x є членом s, і `False` в іншому випадку. `x not in s` повертає заперечення `x in s`. Усі вбудовані послідовності та типи наборів підтримують це, а також словник, для якого `in` перевіряє, чи має словник заданий ключ. Для типів контейнерів, таких як список, кортеж, набір, frozenset, dict або collections.deque, вираз `x in y` еквівалентний `any(x is e or x == e for e in y)`.

Для типів рядків і байтів `x в y` є `True` тоді і тільки тоді, коли x є підрядком y. Еквівалентним тестом є `y.find(x) != -1`. Порожні рядки завжди вважаються підрядками будь-яких інших рядків, тому `"" у "abc` поверне `True`.

For user-defined classes which define the `__contains__()` method, `x in y` returns `True` if `y.__contains__(x)` returns a true value, and `False` otherwise.

For user-defined classes which do not define `__contains__()` but do define `__iter__()`, `x in y` is `True` if some value `z`, for which the expression `x is z or x == z` is true, is produced while iterating over `y`. If an exception is raised during the iteration, it is as if `in` raised that exception.

Lastly, the old-style iteration protocol is tried: if a class defines `__getitem__()`, `x in y` is `True` if and only if there is a non-negative integer index i such that `x is y[i] or x == y[i]`, and no lower integer index raises the `IndexError` exception. (If any other exception is raised, it is as if `in` raised that exception).

Оператор `not in` визначено таким, що має зворотне значення істинності `in`.

### 6.10.3. Порівняння тотожності

Оператори `is` і `is not` перевіряють ідентичність об’єкта: `x is y` є істинним тоді і тільки тоді, коли x і y є одним і тим же об’єктом. Ідентичність об’єкта визначається за допомогою функції `id()`. «x не є y» дає зворотне значення істинності. [4]

## 6.11. Логічні операції

    or_test  ::=  and_test | or_test "or" and_test
    and_test ::=  not_test | and_test "and" not_test
    not_test ::=  comparison | "not" not_test

In the context of Boolean operations, and also when expressions are used by control flow statements, the following values are interpreted as false: `False`, `None`, numeric zero of all types, and empty strings and containers (including strings, tuples, lists, dictionaries, sets and frozensets). All other values are interpreted as true. User-defined objects can customize their truth value by providing a `__bool__()` method.

Оператор `not` видає `True`, якщо його аргумент false, `False` в іншому випадку.

Вираз `x і y` спочатку обчислює x; якщо x false, повертається його значення; інакше обчислюється y і повертається отримане значення.

Вираз `x або y` спочатку обчислює x; якщо x істинне, повертається його значення; інакше обчислюється y і повертається отримане значення.

Зауважте, що ані `and`, ані `or` не обмежують значення та тип, які вони повертають, значеннями `False` і `True`, а радше повертають останній оцінений аргумент. Це іноді корисно, наприклад, якщо `s` є рядком, який слід замінити значенням за замовчуванням, якщо він порожній, вираз `s або 'foo'` дає потрібне значення. Оскільки `not` має створити нове значення, воно повертає логічне значення незалежно від типу свого аргументу (наприклад, `not 'foo'` створює `False`, а не `''` .)

## 6.12. Вирази присвоєння

    assignment_expression ::=  [identifier ":="] expression

Вираз присвоєння (іноді його також називають «іменованим виразом» або «моржем») призначає `expression` `identifier`, а також повертає значення `expression`.

Одним із поширених випадків використання є обробка зіставлених регулярних виразів:

    if matching := pattern.search(data):
        do_something(matching)

Або при обробці потоку файлів у частинах:

    while chunk := file.read(9000):
        process(chunk)

Assignment expressions must be surrounded by parentheses when used as expression statements and when used as sub-expressions in slicing, conditional, lambda, keyword-argument, and comprehension-if expressions and in `assert`, `with`, and `assignment` statements. In all other places where they can be used, parentheses are not required, including in `if` and `while` statements.

Added in version 3.8: Перегляньте PEP 572 для отримання додаткової інформації про вирази присвоєння.

## 6.13. Умовні вирази

    conditional_expression ::=  or_test ["if" or_test "else" expression]
    expression             ::=  conditional_expression | lambda_expr

Умовні вирази (іноді їх називають «потрійним оператором») мають найнижчий пріоритет з усіх операцій Python.

Вираз x if C else y спочатку обчислює умову C, а не x. Якщо C істинне, x обчислюється і повертається його значення; інакше обчислюється y і повертається його значення.

Перегляньте PEP 308 для отримання додаткової інформації про умовні вирази.

## 6.14. Лямбда

    lambda_expr ::=  "lambda" [parameter_list] ":" expression

Лямбда-вирази (іноді їх називають лямбда-формами) використовуються для створення анонімних функцій. Вираз `параметри лямбда: вираз` дає об’єкт функції. Безіменний об’єкт поводиться як об’єкт-функція, визначений за допомогою:

    def <lambda>(parameters):
        return expression

Перегляньте розділ Визначення функцій для синтаксису списків параметрів. Зауважте, що функції, створені за допомогою лямбда-виразів, не можуть містити оператори чи анотації.

## 6.15. Списки виразів

    starred_expression       ::=  ["*"] or_expr
    flexible_expression      ::=  assignment_expression | starred_expression
    flexible_expression_list ::=  flexible_expression ("," flexible_expression)* [","]
    starred_expression_list  ::=  starred_expression ("," starred_expression)* [","]
    expression_list          ::=  expression ("," expression)* [","]
    yield_list               ::=  expression_list | starred_expression "," [starred_expression_list]

За винятком випадків, коли є частиною списку або відображення набору, список виразів, що містить принаймні одну кому, дає кортеж. Довжина кортежу — це кількість виразів у списку. Вирази обчислюються зліва направо.

Зірочка `*` позначає iterable unpacking. Його операнд має бути iterable. Ітерація розгортається в послідовність елементів, які включені в новий кортеж, список або набір на місці розпакування.

Added in version 3.5: Ітераційне розпакування в списках виразів, спочатку запропоноване PEP 448.

Added in version 3.11: Any item in an expression list may be starred. See PEP 646.

A trailing comma is required only to create a one-item tuple, such as `1,`; it is optional in all other cases. A single expression without a trailing comma doesn’t create a tuple, but rather yields the value of that expression. (To create an empty tuple, use an empty pair of parentheses: `()`.)

## 6.16. Порядок оцінювання

Python обчислює вирази зліва направо. Зауважте, що під час оцінювання завдання права частина оцінюється перед лівою.

У наступних рядках вирази обчислюватимуться в арифметичному порядку їх суфіксів:

    expr1, expr2, expr3, expr4
    (expr1, expr2, expr3, expr4)
    {expr1: expr2, expr3: expr4}
    expr1 + expr2 * (expr3 - expr4)
    expr1(expr2, expr3, *expr4, **expr5)
    expr3, expr4 = expr1, expr2

## 6.17. Пріоритет оператора

The following table summarizes the operator precedence in Python, from highest precedence (most binding) to lowest precedence (least binding). Operators in the same box have the same precedence. Unless the syntax is explicitly given, operators are binary. Operators in the same box group left to right (except for exponentiation and conditional expressions, which group from right to left).

Зауважте, що порівняння, тести на приналежність і тести ідентичності мають однаковий пріоритет і функцію ланцюжка зліва направо, як описано в розділі Порівняння.

Оператор | опис
--- | ---
`(вирази...)`, `[вирази...]`, `{ключ: значення...}`, `{вирази...}` | Прив’язка або вираз у дужках, відображення списку, відображення словника, відображення набору
`x[index]`, `x[index:index]`, `x(arguments...)`, `x.attribute` | Підписка, нарізка, виклик, посилання на атрибути
`await x` | Очікуйте вираження
`**` | Піднесення до степеня [5]
`+x`, `-x`, `~x` | Позитивне, негативне, побітове НІ
`*`, `@`, `/`, `//`, `%` | Множення, матричне множення, ділення, поверхове ділення, залишок [6]
`+`, `-` | Додавання і віднімання
`<<`, `>>` | Зміни
`&` | Побітове І
`^` | Побітове XOR
`|` | Порозрядне АБО
`in`, `not in`, `is`, `is not`, `<`, `<=`, `>`, `>=`, `!=`, `==` | Порівняння, включаючи тести на приналежність і тести на ідентифікацію
`not x` | Логічне НІ
`and` | Логічне І
`or` | Логічне АБО
`if` – `else` | Умовний вираз
`lambda` | Лямбда-вираз
`:=` | Вираз присвоєння

Виноски

[1]

У той час як `abs(x%y) < abs(y)` є істинним математично, для чисельних чисел це може не бути істинним через округлення. Наприклад, якщо припустити, що платформа Python з плаваючою точкою є числом подвійної точності IEEE 754, для того, щоб `-1e-100 % 1e100` мали той самий знак, що `1e100`, обчислений результат буде `-1e-100 + 1e100`, що чисельно точно дорівнює `1e100`. Функція `math.fmod()` повертає результат, знак якого збігається зі знаком першого аргументу, і тому в цьому випадку повертає `-1e-100`. Який підхід є більш доцільним, залежить від програми.

[2]

Якщо x дуже близький до точного цілого числа, кратного y, через округлення `x//y` може бути на одиницю більшим за `(x-x%y)//y`. У таких випадках Python повертає останній результат, щоб зберегти те, що `divmod(x,y)[0] * y + x % y` буде дуже близьким до `x`.

[3]

Стандарт Unicode розрізняє code points (наприклад, U+0041) і abstract characters (наприклад, «ЛАТИНСЬКА ВЕЛИКА ЛІТЕРА A»). У той час як більшість абстрактних символів у Unicode представлено лише за допомогою однієї кодової точки, існує ряд абстрактних символів, які, крім того, можуть бути представлені за допомогою послідовності з кількох кодових точок. Наприклад, абстрактний символ «ВЕЛИКА ЛАТИНСЬКА ЛІТЕРА C З ЦЕДІЛЬЄЮ» може бути представлений як один precomposed character у позиції коду U+00C7 або як послідовність base character у позиції коду U+0043 (ВЕЛИКА ЛАТИНСЬКА ЛІТЕРА C), за якою йде combining character у позиції коду U+0327 (КОМБІНУЮЧА CEDILLA).

Оператори порівняння рядків порівнюються на рівні кодових точок Unicode. Людям це може бути не зрозуміло. Наприклад, `"\u00C7" == "\u0043\u0327"` є `False`, навіть якщо обидва рядки представляють той самий абстрактний символ «ЛАТИНСЬКА ВЕЛИКА ЛІТЕРА C З ЦЕДІЛЬЄЮ».

Щоб порівняти рядки на рівні абстрактних символів (тобто інтуїтивно зрозумілим людям), використовуйте `unicodedata.normalize()`.

[4]

Завдяки автоматичному збиранню сміття, вільним спискам і динамічній природі дескрипторів ви можете помітити, здавалося б, незвичайну поведінку в певних випадках використання оператора `is`, як-от порівняння між методами екземплярів або константами. Щоб дізнатися більше, перегляньте їхню документацію.

[5]

Оператор степені `**` прив’язує менш тісно, ніж арифметичний або порозрядний унарний оператор справа, тобто `2**-1` дорівнює `0,5`.

[6]

Оператор `%` також використовується для форматування рядків; застосовується той самий пріоритет.