Python: Списки
2026-02-26 16:28 Diff

Работать с одиночными элементами вы уже умеете. Настало время перейти к очень интересному инструменту, который Python предоставляет для работы с целыми подмножествами элементов списка - срезы (slices).

Синтаксис срезов

Срез записывается так же, как записывается обращение к элементу списка по индексу:

У среза три параметра:

  • START — индекс первого элемента в выборке
  • STOP — индекс элемента списка, перед которым срез должен закончиться. Сам элемент с индексом STOP не будет входить в выборку
  • STEP — шаг выбираемых индексов

При этом любой из трех параметров среза может быть пропущен и вместо соответствующего параметра будет значение по умолчанию:

  • По умолчанию START означает «от начала списка».
  • По умолчанию STOP означает «до конца списка включительно».
  • По умолчанию STEP означает «брать каждый элемент».

Вот несколько примеров с разными наборами параметров:

  • [:] или [::] — весь список.
  • [::2] — нечетные по порядку элементы.
  • [1::2] — четные по порядку элементы.
  • [::-1] — все элементы в обратном порядке.
  • [5:] — все элементы, начиная с шестого.
  • [:5] — все элементы, не доходя до шестого.
  • [-2:1:-1] — все элементы от предпоследнего до третьего в обратном порядке. Во всех случаях выборки от большего индекса к меньшему нужно указывать шаг.

Теперь разберем как можно использовать срезы.

Выборка элементов

Срезы работают не только со списками, но и с кортежами, и даже со строками. Результатом применения выборки всегда становится новое значение соответствующего типа — список, кортеж, строка:

Присваивание срезу

В отличие от строк и кортежей списки могут изменяться. Одним из вариантов модификации является присваивание срезу. Срезу с указанным шагом можно присвоить список из новых элементов:

Срез [::2] означает, что мы выбираем элементы с шагом 2, то есть берем каждый второй элемент. Список [0, 0, 0] - это список, который мы присваиваем выбранным элементам. Срез l[::2] теперь содержит элементы с индексами 0, 2 и 4 (т.е. 1, 3 и 5). Присваивание [0, 0, 0] этим элементам заменяет их на нули. В результате изменения списка l становится равным [0, 2, 0, 4, 0, 6].

Если вы попробуете присвоить срезу с шагом неверное количество элементов, то получите ошибку:

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

Сначала список растет, потом уменьшается, а под конец вообще становится пустым — и все с помощью компактного, но мощного синтаксиса срезов.

Срезы-значения

Хоть срезы и имеют специальную поддержку со стороны синтаксиса, но мы можем создавать и использовать срезы сами по себе — как обычные значения.

Значение среза можно сконструировать с помощью функции slice():

Функция slice() принимает от одного до трех параметров — те самые START, STOP и STEP. При вызове функции с одним параметром, функция вызывается с параметром STOP.

Если вы хотите пропустить один из параметров, то подставьте вместо него None. Также None можно использовать и в записи срезов в квадратных скобках — там он так же будет означать пропуск значения.

На месте параметров среза могут быть любые выражения, лишь бы эти выражения вычислялись в целые числа или None.

Соотношение START и STOP

В срезе элемент с индексом STOP не включается в результат, в отличие от элемента с индексом START.

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

Посмотрим на такой пример:

Это свойство удобно использовать, когда вы разбираете некий текст. Вам достаточно двигать позицию разрезания строки на начало и остаток, не заботясь, что какая-либо информация на границе разрезания потеряется.