БэкендPython

TypeError в Python: как исправить сложение строки и числа

Разбираем TypeError при сложении str и int: почему input возвращает строку, когда использовать int, str и f-строку, как проверить типы.

Кодик

Автор

5 мин чтения

TypeError при сложении строки и числа означает конфликт операций: + складывает числа или соединяет строки, но не угадывает, какое преобразование вы имели в виду. Если значение участвует в расчёте, преобразуйте его в int или float на входе. Если задача состоит только в выводе, используйте f-строку. Перед правкой проверьте оба операнда через type и repr.

Одинаково выглядящие значения могут иметь разные типы. Число 16 можно увеличить, а строка "16" состоит из символов. Функция input() всегда возвращает строку, даже если человек набрал только цифры. Поэтому ошибка часто появляется в первой программе с возрастом, ценой или количеством.

1Вычисление

Для математики преобразуйте текст в число до операции.

2Представление

Для сообщения не складывайте типы, а форматируйте строку.

3Граница

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

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

Для целых чисел + означает арифметическое сложение, а для строк конкатенацию. Выражение со смешанными типами неоднозначно: "16" + 1 могло бы означать 17, строку "161" или ошибку ввода. Python выбирает явную ошибку, чтобы программа не получила тихий неверный результат.

age = input('Сколько вам лет? ')
print(type(age), repr(age))
# <class 'str'> '16'

next_age = age + 1
# TypeError: can only concatenate str (not "int") to str
ОперандыЧто означает плюсРезультат
2 + 3Сложение целых чисел5
"2" + "3"Соединение строк"23"
"2" + 3Неоднозначная смешанная операцияTypeError
int("2") + 3Явное преобразование для расчёта5
f"Ответ: {3}"Форматирование для вывода"Ответ: 3"

Конфликт типов str и int при операторе плюс в Python
Оператор плюс не выбирает между арифметикой и соединением текста за разработчика.

Смотрите не только на тип, но и на содержимое. repr(value) покажет кавычки и пробелы. Строка " 16 " обычно корректно преобразуется через int, а "16 лет" уже потребует проверки или отдельного разбора. Не удаляйте символы вслепую.

Когда использовать int, float, str и f-строку

Определите цель значения
  1. Назовите операцию: расчёт, сравнение, хранение идентификатора или вывод.
  2. Для целого количества используйте int.
  3. Для дробного измерения используйте float и учитывайте формат ввода.
  4. Для сообщения используйте f-строку, не меняя исходный тип.
  5. Для кода, телефона и артикула оставляйте строку, даже если там цифры.
  6. Проверьте пустую строку и ввод с буквами до преобразования.

Преобразование выбирают по смыслу, а не по внешнему виду. Почтовый индекс или номер заказа могут содержать ведущие нули и не участвуют в математике, поэтому им подходит str. Количество товаров должно быть целым. Цена часто требует десятичной модели, а для учебного примера можно начать с float.

raw_count = input('Количество: ')
count = int(raw_count)
price = 250
total = count * price

print(f'Товаров: {count}')
print(f'Сумма: {total} руб.')

Выбор int float str или f строки по смыслу значения
Тип выбирают по операции: вычисление, идентификатор или представление.

Преобразуйте один раз на границе

После count = int(raw_count) внутри программы работает уже число. Не вызывайте int в каждой формуле: это усложняет код и разбрасывает обработку неверного ввода по нескольким местам.

Как безопасно обработать пользовательский ввод

Явное преобразование может вызвать ValueError, если строка не является целым числом. Это следующий, более точный уровень диагностики: тип входа ожидаемо строковый, но его значение не подходит. Обработайте этот случай рядом с вводом и не продолжайте расчёт с выдуманным нулём.

ВводintРешение
"16"16Продолжить расчёт
" 16 "16Пробелы допустимы
Пустая строкаValueErrorПопросить значение повторно
"16.5"ValueErrorРешить, допустимо ли дробное число
"16 лет"ValueErrorНе смешивать число и единицу во входе
raw_age = input('Возраст: ').strip()

try:
    age = int(raw_age)
except ValueError:
    print('Введите возраст целым числом, например 16')
else:
    print(f'Через год вам будет {age + 1}')

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

Не используйте isdigit как полную замену преобразованию. isdigit() не принимает знак минус и не отвечает на вопрос о допустимом диапазоне. Для большинства программ проще попытаться выполнить int, перехватить ожидаемый ValueError, а затем отдельно проверить границы.

Почему быстрые исправления дают неверный результат

Преобразовать число в строку легко, но это может изменить смысл задачи. age + str(1) для строки "16" даст "161", а не 17. Обратная крайность состоит в вызове int у любого поля, включая номер телефона. Исправление должно следовать типу данных предметной области.

Делать str у числа в расчёте

Ошибка исчезнет, но сложение превратится в соединение текста.

Вызывать int только в print

Остальные вычисления продолжат работать со строкой. Преобразуйте значение на входе.

Скрывать ValueError нулём

Неверный ввод станет реальным заказом с количеством 0. Лучше попросить исправление.

Проверять только один операнд

Вторая переменная могла прийти из JSON, CSV или формы строкой. Выведите обе пары type и repr.

Тип является частью контракта функции

Если функция считает сумму, передавайте ей числа и проверяйте ввод до вызова. Тогда внутри формулы не нужны догадки и повторные преобразования, а тесты могут отдельно проверить расчёт и отдельно пользовательский ввод.

Практика: калькулятор стоимости без TypeError

Разделите маленькую программу на два слоя. Функция calculate_total принимает целое количество и цену. Внешний код получает строку, преобразует её и сообщает об ошибке. Такая структура остаётся понятной, когда вместо терминала появится форма или API.

Проверка решения
  1. Выведите type и repr обоих операндов до исправления.
  2. Определите, нужен расчёт или только строковое сообщение.
  3. Преобразуйте ввод в число ровно один раз.
  4. Обработайте пустую строку и буквы через ValueError.
  5. Проверьте значение 0 и отрицательное число по правилам задачи.
  6. Используйте f-строку для результата, не складывая текст и число.
Проверяйте результат, а не только отсутствие ошибки. Для ввода 2 и цены 250 программа должна вывести 500, а не "2250" и не "250250". Запишите ожидаемый ответ до запуска: это сразу обнаруживает случайную конкатенацию строк.
Короткие ответы
Какой тип возвращает input?

Всегда str, даже если пользователь ввёл только цифры.

Почему Python не превращает строку в число автоматически?

Ожидаемый смысл неоднозначен: нужны арифметика, соединение текста или сообщение о неверном вводе.

Когда применять str?

Когда действительно нужно строковое представление. Для сообщений обычно удобнее f-строка.

Чем проверить скрытые пробелы?

Используйте repr(value), который покажет кавычки и управляющие символы.

Что делать с буквами при int?

Перехватить ожидаемый ValueError рядом с вводом и попросить корректное значение.

Отделите ввод от вычисления

Потренируйтесь с типами и условиями в курсе Python. Для полной схемы диагностики откройте 15 частых ошибок новичков и руководство по первому Python-скрипту.

Если преобразование уже вызывает другое сообщение, материал про if, elif и else поможет построить понятные ветки. В Кодике можно держать рядом пример входа, ожидаемый тип и проверочный вывод.