Перейти к основному содержимому

Работа с типами данных в Python

Разработчику Архитектору

См. также: Типы данных в Python · Даты и время в Python · Справочник Python

Дальше: обзор типов — Типы данных; таблицы операций с list, dict, setв той же статье.


Работа с типами данных в Python

Преобразование типов

Преобразование типов — процесс изменения типа объекта путём интерпретации его значения в контексте другого типа. В Python различают явное (принудительное) и неявное (автоматическое) приведение типов. Явные преобразования осуществляются с помощью встроенных конструкторов типов.

Основные функции преобразования:

  • int(x) — преобразует x в целое число. При преобразовании строки она должна содержать корректное целочисленное представление (возможно с знаком). При преобразовании числа с плавающей точкой отбрасывается дробная часть (усечение к нулю, а не округление). Примеры: int("42") → 42, int(3.9) → 3.
  • float(x) — преобразует x в число с плавающей точкой. Поддерживает строки с десятичной записью, экспоненциальной формой ("1e3"), а также inf, nan. Примеры: float("3.14") → 3.14, float(5) → 5.0.
  • str(x) — возвращает строковое представление объекта. Вызывает метод __str__() объекта. Для встроенных типов результат обычно человеко-читаем. Пример: str(123) → "123", str(True) → "True". Аналогично int(x) и bool(x) вызывают __int__() и __bool__() у пользовательских классов — см. дандер-методы.
  • bool(x) — возвращает True или False в соответствии с логическим значением объекта. Следует помнить, что в Python большинство объектов имеют "истинное" значение, за исключением None, False, 0, 0.0, 0j, пустых коллекций и строк ("", [], {}), и объектов с переопределенным __bool__() или __len__(), возвращающим 0. bool не является просто "обёрткой" вокруг 0/1. Это полноценный тип, наследуемый от int, где True == 1, False == 0, но это не означает эквивалентности семантики.

Преобразование в целое число

<целое_число> = int(<значение>)
  • <значение> — строка с корректным целочисленным представлением, число с плавающей точкой или любой объект, допускающий приведение к int.
  • Результат — целое число без дробной части. При преобразовании из float происходит усечение к нулю.

Преобразование в число с плавающей точкой

<вещественное_число> = float(<значение>)
  • <значение> — строка с десятичной записью, экспоненциальной формой ("1e3"), специальные значения ("inf", "nan"), целое число или другой объект, допускающий приведение к float.
  • Результат — число типа float.

Преобразование в строку

<строка> = str(<объект>)
  • <объект> — любой объект Python.
  • Результат — человеко-читаемое строковое представление, полученное вызовом метода __str__() объекта.

Преобразование в логическое значение

<логическое_значение> = bool(<объект>)
  • <объект> — любой объект Python.
  • Результат — True для "истинных" значений, False для "ложных" (например, None, 0, "", [], {}, False и т.д.).

Статическая типизация и аннотации

Несмотря на динамическую природу Python, в современной разработке активно применяются инструменты статической типизации. Они позволяют выявлять ошибки на этапе анализа кода, улучшать автодополнение в IDE и документировать сигнатуры функций.

Статическая типизация реализуется через аннотации типов (PEP 484) и сторонние анализаторы.

Аннотации типов добавляются с помощью синтаксиса:

def process_data(value: str) -> int:
return len(value)

Они не влияют на выполнение программы, но доступны через __annotations__ и используются анализаторами.

Инструменты статического анализа:

  • mypy — один из первых и наиболее распространённых статических анализаторов. Проверяет соответствие аннотаций типов, включая сложные случаи — объединения (Union), опциональные типы (Optional), дженерики.
  • pyright — анализатор от Microsoft, написанный на TypeScript, интегрирован в VS Code. Отличается высокой скоростью и хорошей поддержкой современных возможностей Python (например, LiteralString, TypeGuard).
  • pyre — разработан Facebook (Meta), ориентирован на производительность при анализе больших проектов. Менее популярен, но эффективен в специфических средах.
  • Pydantic — не является анализатором типов, но активно использует аннотации для валидации данных при создании моделей. Обеспечивает runtime-проверку типов на основе схем, что делает его мощным инструментом для API и конфигураций.

Cтатическая типизация в Python — опциональна и не заменяет тестирование. Она снижает вероятность определённых классов ошибок, но не гарантирует корректность логики.


Операторы

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


Арифметические

ОператорДействиеПример
+сложение4 + 59
-вычитание8 - 35
*умножение5 * 525
/деление (результат всегда float)4 / 22.0
//целочисленное деление (вниз)15 // 43
%остаток от деления7 % 21
**степень2 ** 38

Присваивания с операцией

Сокращённая запись меняет переменную "на месте":

ЗаписьТо же самое
x += 3x = x + 3
x -= 3x = x - 3
x *= 3x = x * 3
x /= 3x = x / 3
x //= 3x = x // 3
x **= 2x = x ** 2

Оператор присваивания-выражения (:=, walrus)

Оператор walrus (:=, от англ. walrus operator — "моржовый оператор" из-за формы : и =) присваивает значение переменной внутри выражения. Появился в Python 3.8+.

Синтаксис:

(имя := выражение)

Выражение с := возвращает присвоенное значение, поэтому его можно встроить в условие if, заголовок while, списочное включение или любое другое выражение.

Без walrus длину списка приходится сохранять отдельной строкой:

data = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11]

n = len(data)
if n > 10:
print(f"{n} items")

С walrus присваивание и проверка объединяются:

if (n := len(data)) > 10:
print(f"{n} items")

Разбор:

  • len(data) вычисляется один раз, результат сохраняется в n.
  • Условие сравнивает n с 10; при истине в теле if переменная n уже доступна.
  • Скобки вокруг (n := len(data)) обязательны — без них интерпретатор выдаст SyntaxError из-за приоритета операторов.

Практические примеры в if и while — в управляющих конструкциях.

Когда walrus уместен:

  • значение нужно вычислить один раз и сразу использовать в условии или в теле блока;
  • переменная — временная (длина коллекции, результат функции, строка ввода).

Когда лучше обычное присваивание:

  • переменная используется во многих местах функции — вынесите n = ... отдельной строкой;
  • выражение длинное или с побочными эффектами — читаемость важнее краткости.

См. также синтаксический сахар — walrus отнесён к лексемному сахару.


Сравнение

Возвращают True или False==, !=, >, <, >=, <=.

print(10 == 10) # True
print(10 != 5) # True

Разбор:

  • == проверяет равенство значений.
  • != проверяет различие значений.
  • оба оператора возвращают bool, поэтому результат сразу готов для if и логических выражений.

Для проверки "тот же объект в памяти", а не просто одинаковое значение, используйте is и is not (часто с None):

value = None
if value is None:
print("значения нет")

a = [1, 2]
b = [1, 2]
print(a == b) # True — одинаковое содержимое
print(a is b) # False — два разных списка

Логические

ОператорСмысл
andистина, если оба условия истинны
orистина, если хотя бы одно истинно
notинверсия результата
age = 20
print(age >= 18 and age < 65) # True
print(not (age < 18)) # True

Принадлежность

Проверяют, есть ли элемент в последовательности (строка, список, кортеж, множество, ключи словаря):

fruits = ["яблоко", "банан", "вишня"]
print("банан" in fruits) # True
print("груша" not in fruits) # True

text = "Привет"
print("ив" in text) # True — подстрока

Разбор:

  • in запускает проверку принадлежности в коллекции или подстроки в строке.
  • not in инвертирует результат.
  • для list операция проходит по элементам, для str ищется вхождение подстроки.

Побитовые операторы (&, |, ^, ~, <<, >>) нужны реже — в основном для низкоуровневой работы с числами; подробнее в статье про синтаксис.


Работа с числами

Числовые типы в Python включают int, float, complex и decimal.Decimal (из стандартного модуля decimal). Рассмотрим основные операции и особенности.


Арифметические операции

Арифметические операции:

  • +, -, *, / — обычное деление (всегда возвращает float)
  • // — целочисленное деление (floor division)
  • % — остаток от деления
  • ** — возведение в степень
  • -x, +x — унарные операции

Из особенностей, можно отметить следующее -

  • деление / всегда возвращает float, даже если операнды делятся нацело;
  • целочисленное деление // округляет вниз (к меньшему целому), включая отрицательные числа: -7 // 2 = -4;
  • приоритет операций следует математическим правилам; для группировки используются скобки.

Модуль math

В стандартной библиотеке имеется модуль math, который можно добавить командой import math и использовать расширенные математические операции.


import math

print(math.pi) # 3.1415...
print(math.sqrt(25)) # 5.0

Разбор:

  • import math подключает модуль со стандартными математическими функциями.
  • math.pi возвращает константу числа pi.
  • math.sqrt(25) вычисляет квадратный корень и возвращает float.

Округление

Python предоставляет несколько способов округления:

  • round(x) — стандартное округление к ближайшему чётному при равенстве расстояний (банковское округление). Пример: round(2.5) → 2, round(3.5) → 4.
  • math.floor(x) — округление вниз.
  • math.ceil(x) — округление вверх.
  • math.trunc(x) — усечение дробной части (эквивалентно int(x) для положительных).

Модуль decimal

Для задач, требующих точной арифметики (финансовые расчёты, измерения), рекомендуется использовать тип Decimal из модуля decimal. Он представляет числа в виде десятичных дробей, избегая ошибок двоичного округления (0.1 + 0.2 != 0.3 в float). Точность и режим округления настраиваются через контекст (getcontext()). Операции выполняются медленнее, чем с float, но обеспечивают предсказуемость.

from decimal import Decimal, getcontext
getcontext().prec = 6
result = Decimal('0.1') + Decimal('0.2') # → Decimal('0.3')

Разбор:

  • Decimal('0.1') берет значение из строки, поэтому хранит десятичное число точно.
  • getcontext().prec = 6 задает рабочую точность операций Decimal.
  • сумма 0.1 + 0.2 в Decimal дает ожидаемый десятичный результат без двоичной погрешности float. Не следует сравнивать float на равенство. Вместо этого используйте math.isclose().

Работа со строками

Строки в Python — неизменяемые последовательности Unicode-символов (тип str). Поддерживают широкий набор операций и методов.


Конкатенация и повторение

Конкатенация: s1 + s2, через оператор "+".

Повторение: s * n (где n — целое).

Не рекомендуется использовать + в цикле для сборки строк — из-за неизменяемости каждый раз создаётся новый объект. Вместо этого следует использовать ''.join(iterable).

Пример конкатенации:

s1 = "Текст"
s2 = " и ещё текст."
print(s1 + s2)

Результат: Текст и ещё текст.

first = "Привет"
second = "мир"
result = first + " " + second + "!"
print(result) # Привет мир!

Пример повторения:

s = "Текст"
print(s * 3)

Результат будет "ТекстТекстТекст".

laugh = "ха"
print(laugh * 5) # хахахахаха

line = "-=" * 10
print(line) # -=-=-=-=-==-=-=-=-=-=-

Форматирование строк

Существует несколько подходов:


f-строки (PEP 498)

name = "Alice"
print(f"Hello, {name}!")

F-строка означает "formatted string". Синтаксис подразумевает добавление буквы f перед текстом. Он позволяет подставлять переменные через фигурные скобки - {имя_переменной}.

Поддерживают выражения, вызовы функций, форматирование `(:

  • .2f;
  • !r;
  • т.д.)`.
name = input("Введите имя: ")

print(f"Твоё имя: {name}")
print(f"Первая буква: {name[0]}")
print(f"Последняя буква: {name[-1]}")
print(f"Длина имени: {len(name)} букв")
print(f"Имя заглавными: {name.upper()}")

Разбор:

  • input(...) читает строку из stdin.
  • в f"..." выражения в {} вычисляются во время формирования строки.
  • name[0] и name[-1] обращаются к первому и последнему символам.
  • len(name) возвращает длину строки, upper() строит новую строку в верхнем регистре.

Метод .format()

"Hello, {}!".format(name)
"Value: {value:.2f}".format(value=3.1415)

Здесь принцип похож на f-строки, но подразумевает более неудобный синтаксис - нужно расставить в текст фигурные скобки {}, а уже после текста добавить вызов метода format() и в параметрах передать переменную или значение переменной.


% formatting

"Hello, %s!" % name

% подразумевает подстановку значения с использованием особого форматирования:

  • '%d', '%i', '%u' - десятичное число;
  • '%o' - число в восьмеричной системе счисления;
  • '%x' - число в шестнадцатеричной системе счисления (буквы в нижнем регистре);
  • '%X' - число в шестнадцатеричной системе счисления (буквы в верхнем регистре);
  • '%e' - число с плавающей точкой с экспонентой (экспонента в нижнем регистре);
  • '%E' - число с плавающей точкой с экспонентой (экспонента в верхнем регистре);
  • '%f', '%F' - число с плавающей точкой (обычный формат);
  • '%g' - число с плавающей точкой. с экспонентой (экспонента в нижнем регистре), если она меньше, чем -4 или точности, иначе обычный формат;
  • '%G' - число с плавающей точкой. с экспонентой (экспонента в верхнем регистре), если она меньше, чем -4 или точности, иначе обычный формат;
  • '%c' - символ (строка из одного символа или число - код символа);
  • '%s' - строка;
  • '%%' - знак "%".

Учитывая "замудрённость" подходов, очевидно, что лучше использовать первый метод, f-строки.


Срезы (slicing) и доступ по индексу

Слово "PYTHON" — это 6 ячеек:

Буква
P - 0
Y - 1
T - 2
H - 3
O - 4
N - 5

Доступ к символам — [0], [1], [-1]

word = "Привет"

print(word[0]) # П — первая буква
print(word[1]) # р
print(word[5]) # т — шестая буква
print(word[-1]) # т — последняя (отсчёт с конца!)
print(word[-2]) # е — предпоследняя

Строки поддерживают доступ по индексу и срезы:

  • s[i] — символ по индексу (от 0 до len(s)-1, отрицательные индексы отсчитываются с конца).
  • s[start:stop:step] — срез.

Примеры:

  • s[1:4] — символы с 1 по 3.
  • s[::-1] — строка в обратном порядке (для списков — разворот).
  • s[::2] — каждый второй символ.
s = "Текст"
print(s[1:4])

Результат будет "екс".

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


Методы для работы со строками

У типа str десятки методов; в повседневном коде чаще всего встречаются регистр, поиск и подсчёт, обрезка, замена и разбиение, выравнивание и проверки содержимого. Вызов всегда через точку: "текст".upper(). Методы, которые "меняют" строку, возвращают новую str, исходная остаётся прежней.

Для поиска по шаблону, а не по точной подстроке, используют модуль re и справочник RegEx.

Полный перечень — в справочнике Python (тип str).

Сводка — 14 частых методов

МетодНазначениеПримерРезультат
capitalize()Первая буква заглавная, остальные строчные'hello world'.capitalize()'Hello world'
lower()Все символы в нижнем регистре'HELLO WORLD'.lower()'hello world'
upper()Все символы в верхнем регистре'hello world'.upper()'HELLO WORLD'
center(width[, fillchar])Выравнивание по центру с заполнением'Python'.center(10, '*')'**Python**'
count(sub)Сколько раз встречается подстрока'HELLO WORLD'.count('L')3
index(sub)Индекс первого вхождения; иначе ValueError'HELLO WORLD'.index('O')4
find(sub)Индекс первого вхождения; иначе -1'HELLO WORLD'.find('OR')7
replace(old, new)Замена подстроки'31/01/2022'.replace('/', '-')'31-01-2022'
split(sep)Разбиение в список по разделителю'31/01/2022'.split('/')['31', '01', '2022']
strip([chars])Убрать пробелы (или указанные символы) с концов' x '.strip()'x'
isalnum()Только буквы и цифры'abc123'.isalnum()True
isnumeric()Символы — цифры (в т.ч. дроби Unicode)'12345'.isnumeric()True
islower()Все буквы в нижнем регистре'hello world'.islower()True
isupper()Все буквы в верхнем регистре'HELLO WORLD'.isupper()True

Для каждого слова с заглавной буквы используйте title(), а не capitalize():

"hello world".title() # 'Hello World'
"hello world".capitalize() # 'Hello world'

Регистр и выравнивание

s = "hello WORLD"
print(s.capitalize()) # Hello world
print(s.lower()) # hello world
print(s.upper()) # HELLO WORLD
print("Python".center(10, "*")) # **Python**

Поиск и подсчёт

find и index ищут подстроку и возвращают индекс первого символа совпадения (отсчёт с нуля). Разница в ошибке: find вернёт -1, index выбросит ValueError.

text = "HELLO WORLD"
print(text.count("L")) # 3
print(text.index("O")) # 4 — буква O в HELLO
print(text.find("OR")) # 7 — подстрока OR в WORLD
print(text.find("XYZ")) # -1 — не найдено

Оператор in проверяет наличие подстроки без индекса: 'OR' in textTrue.

Замена и разбиение

Метод replace возвращает новую строку с подстановкой. Третий аргумент count ограничивает число замен.

date = "31/01/2022"
print(date.replace("/", "-")) # 31-01-2022
print(date.split("/")) # ['31', '01', '2022']

path = "a/b/c"
print(path.split("/")) # ['a', 'b', 'c']
print(path.split("/", maxsplit=1)) # ['a', 'b/c'] — разрез только по первому "/"
print(path.rsplit("/", 1)) # ['a/b', 'c'] — разрез только по последнему "/"

split() без аргумента делит строку по пробельным символам (пробел, таб \t, перевод строки). Несколько пробелов подряд считаются одним разделителем:

"Python это круто".split() # ['Python', 'это', 'круто']

splitlines() делит текст на строки по символам конца строки — \n, \r\n (Windows), \r (старый Mac). Удобно после read() из файла, когда ОС могла записать разные переводы строк:

"Первая\nВторая\r\nТретья".splitlines() # ['Первая', 'Вторая', 'Третья']

partition(sep) и rpartition(sep) делят строку ровно на три части и возвращают кортеж (неизменяемый список из трёх элементов):

  • текст до разделителя;
  • сам разделитель;
  • текст после разделителя.

partition ищет разделитель слева, rpartitionсправа. Если разделитель не найден, кортеж всё равно из трёх элементов (часть из них пустая):

"login@domain.ru".partition("@") # ('login', '@', 'domain.ru')
"file.tar.gz".rpartition(".") # ('file.tar', '.', 'gz')

Список частей собирают обратно через join: разделитель пишут слева от точки — "-".join(["31", "01", "2022"])'31-01-2022'.

Обрезка по краям и цепочка strip → split

Методы strip, lstrip, rstrip убирают пробельные символы с концов строки.

  • strip() — с обоих концов;
  • lstrip() — только слева;
  • rstrip() — только справа.

Необязательный аргумент задаёт набор символов для удаления с краёв (не целую подстроку посередине):

" привет \n".strip() # 'привет'
"!!!текст!!!".strip("!") # 'текст'

Типичная обработка строки из файла или формы — три шага:

  1. strip() у всей строки (убрать пробелы и \n по краям).
  2. split(',') по разделителю полей.
  3. strip() у каждого элемента списка.

Пример и кросс-языковые варианты — в Продвинутые операции с данными.

raw_line = " Анна, 25, программист \n"

parts = raw_line.strip().split(",") # ['Анна', ' 25', ' программист']
final = [item.strip() for item in parts] # ['Анна', '25', 'программист']

", ".join(final) # 'Анна, 25, программист'

Если между запятыми нет символов, split оставляет пустой элемент: "a,,b".split(",")['a', '', 'b']. Как отфильтровать пустые поля в разных языках — в разделе частые ошибки.

Для разбиения по шаблону RegEx см. модуль re в начале раздела.

Проверки содержимого

Методы с префиксом is… возвращают bool и не меняют строку.

print("abc123".isalnum()) # True — буквы и/или цифры, без пробелов
print("12345".isnumeric()) # True — цифровые символы (шире, чем isdigit)
print("hello world".islower()) # True
print("HELLO WORLD".isupper()) # True
print("Hello".islower()) # False — есть заглавная H

isdigit() — только ASCII-цифры 09; для пользовательского ввода чаще сочетают с int() и обработкой исключений.

Ещё полезные методы

МетодНазначение
startswith(prefix), endswith(suffix)Проверка начала и конца строки
removeprefix(prefix), removesuffix(suffix)Убрать заданный префикс или суффикс целиком, если он совпал (Python 3.9+)
replace(old, new[, count])Замена подстроки во всём тексте
join(iterable)Склейка списка строк; вызывается у строки-разделителя

removeprefix / removesuffix снимают целую подстроку с начала или конца, если она совпала (например "photo_" или ".jpg"). strip("!") удаляет с краёв любой символ из переданного набора, пока он повторяется.

"file.txt".endswith(".txt") # True
"photo_2023.jpg".removeprefix("photo_") # '2023.jpg'
"photo_2023.jpg".removesuffix(".jpg") # 'photo_2023'

Таблица trim / split / join в Python, Java, C#, PHP, Kotlin, Groovy, C++ и JavaScript.

Неизменяемость str

После s.upper() переменная s не меняется. Чтобы сохранить результат, присвойте его: s = s.strip().lower().


Работа с булевыми значениями

Тип bool — подкласс int, содержащий два значения: True и False. Используется для логических выражений, условий и управления потоком выполнения.


Логические операторы

Логические операторы

  • and — логическое И (возвращает последнее истинное или первое ложное значение).
  • or — логическое ИЛИ (возвращает первое истинное или последнее ложное).
  • not — логическое НЕ (возвращает True или False).

Операторы поддерживают ленивую (short-circuit) семантику: второе выражение вычисляется только при необходимости.

x = a and b # если a — False, b не вычисляется

Сравнения

Операторы сравнения (==, !=, <, <=, >, >=) возвращают bool.

  • == проверяет равенство значений, is — идентичность объектов.
  • Сравнение разных типов возможно, но может давать неочевидные результаты (например, 1 == True — True, так как bool — подкласс int).
  • Избегайте сравнения float на равенство; используйте math.isclose().

Любой объект может быть интерпретирован в булевом контексте (в if, while, and/or). Пустые или нулевые значения считаются ложными, остальные — истинными.


Работа с датами и временем

Модуль datetime предоставляет средства для работы с датами, временем и интервалами. Основные типы:

  • datetime.datetime — комбинированный объект дата+время.
  • datetime.date — только дата.
  • datetime.time — только время.
  • datetime.timedelta — разница между двумя моментами времени.
  • datetime.timezone — информация о часовом поясе.

Создание объектов

from datetime import datetime, date, timezone

now = datetime.now() # текущие дата и время
utc_now = datetime.now(timezone.utc)
specific = datetime(2025, 4, 5, 12, 30, 0)
today = date.today()

Форматирование

Форматирование и парсинг:

  • strftime(format) — форматирование в строку.
  • strptime(string, format) — парсинг строки в объект.
dt = datetime(2025, 4, 5)
dt.strftime("%Y-%m-%d") # → "2025-04-05"
datetime.strptime("2025-04-05", "%Y-%m-%d")

now = datetime.now()
print(f"{now.day:02d}.{now.month:02d}.{now.year}") # → "05.04.2025"
print(f"{now.hour:02d}:{now.minute:02d}:{now.second:02d}") # → "14:30:00"

Разбор:

  • strftime переводит объект даты/времени в строку по шаблону формата.
  • %Y, %m, %d означают год, месяц и день; %H, %M, %S — час, минуты и секунды.
  • f-строки с :02d дают те же двузначные компоненты через атрибуты .day, .month, .hour и т.д.
  • strptime выполняет обратную операцию: читает строку и создает datetime.

strptime чувствителен к формату и выбрасывает ValueError при несоответствии. Подробнее о двух способах форматирования — в Даты и время в Python.


Работа с временем

Операции с временем:

timedelta позволяет прибавлять/вычитать интервалы:

from datetime import timedelta
tomorrow = now + timedelta(days=1)

Разницу между двумя datetime можно получить как timedelta.

Рекомендуется работать с UTC внутри системы и конвертировать в локальное время только на вывод. timezone.utc — константа для UTC.

Для сложных сценариев (летнее время, правила перехода) используется сторонняя библиотека pytz или встроенный zoneinfo (начиная с Python 3.9).