Написать пост

Работа со строками в Python. Готовимся к собеседованию: вспоминаем азы

Аватар Типичный программист

Смотрим на строки в Python глазами интервьюера на собеседовании и разбираем базовые операции.

Обложка поста Работа со строками в Python. Готовимся к собеседованию: вспоминаем азы

В этой статье мы разберем работу со строками в Python с необычного угла — глазами интервьюера на собеседовании. Информация будет полезна как новичку, так и уверенному джуну. В первой части поговорим о базовых операциях. Во второй — разберем примеры задач и вопросов, к которым стоит быть готовым.

Итак, мы на собеседовании, и я хочу узнать, умеете ли вы обращаться со строками.

Как склеить две строки?

			>>> s = "abc" + "def"
>>> s += "xyz"
		

Элементарно? Почти. Важно помнить, что строки — это неизменяемые объекты. Каждый раз, когда мы говорим про «изменение» строки, технически мы создаем новый объект и записываем туда вычисленное значение.

А как склеить три строки? Напрашивается ответ «точно так же», и иногда это самый лучший способ. Но интервьюер скорее всего хочет проверить, знаете ли вы про метод .join().

			>>> names = ["John", "Paul", "Ringo", "George"]
>>> ", ".join(names)
'John, Paul, Ringo, George'
		

join() — очень удобный метод, позволяющий склеить N строк, причём с произвольным разделителем.

Здесь важно не только получить результат, но и понимать, как работает приведённая конструкция. А именно, что join() — это метод объекта «строка», принимающий в качестве аргумента список и возвращающий на выходе новую строку.
Кстати, хорошая задачка для интервью — написать свою реализацию join().

Разделить строки?

Есть несколько способов получить часть строки. Первый — это split, обратный метод для join. В отличие от join’а, он применяется к целевой строке, а разделитель передаётся аргументом.

			>>> s = "Альфа, Браво, Чарли"
>>> s.split(", ")
['Альфа', 'Браво', 'Чарли']
		

Второй — срезы (slices).

Срез s[x:y] позволяет получить подстроку с символа x до символа y. Можно не указывать любое из значений, чтобы двигаться с начала или до конца строки. Отрицательные значения используются для отсчёта с конца (-1 — последний символ, -2 — предпоследний и т.п.).

			>>> s = "Hello, world!"
>>> print(s[0:5])
Hello
>>> print(s[-6:])
world!
		

При помощи необязательного третьего параметра s[x:y:N] можно выбрать из подстроки каждый N-ый символ. Например, получить только чётные или только нечётные символы:

			>>> s = "0123456789"
>>> print(s[::2])
02468
>>> print(s[1::2])
13579
		

Что насчёт поиска в строке?

Самое быстрое — проверить, начинается ли (заканчивается ли) строка с выбранных символов. Для этого в Python предусмотрены специальные строковые методы.

			>>> s = "0123456789"
>>> s.startswith("012")
True
>>> s.endswith("69")
False
		

Для поиск подстроки в произвольном месте есть метод с говорящим названием find(). Он вернет индекс начала найденного вхождения подстроки в строку, либо -1, если ничего не найдено.

			>>> s = "0123456789"
>>> s.find("45")
4
>>> s.find("42")
-1
		

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

			>>> import re
>>> s = "https://www.reg.ru/hosting/";
>>> result = re.match(r"^(http|https)://([^/]+)(.*)$", s)
>>> print(result.group(1))
https
>>> print(result.group(2))
www.reg.ru
>>> print(result.group(3))
/hosting/
		

А замену в строке сделать сможете?

Во-первых, при помощи срезов и склейки строк можно заменить что угодно.

			>>> s = "Hello, darling! How are you?"
>>> s[:7] + "Василий" + s[14:]
'Hello, Василий! How are you?'
		

Во-вторых, умеешь find(), умей и replace().

			>>> s.replace("darling", "Василий")
'Hello, Василий! How are you?'
		

В-третьих, любую проблему можно решить регулярными выражениями. Либо получить две проблемы ? В случае с заменой вам нужен метод re.sub().

			>>> s = "https://www.reg.ru/hosting/";
>>> import re
>>> print(re.sub('[a-z]', 'X', s))
XXXXX://XXX.XXX.XX/XXXXXXX/
		

Посимвольная обработка?

Есть бесчисленное множество задачек, которые можно решить, пройдясь в цикле по строке. Например, посчитать количество букв «о».

			>>> s = "Hello, world!"
>>> for c in s:
>>>     if c == "o":
>>>         counter += 1
>>> print(counter)
2
		

Иногда удобнее бежать по индексу.

			>>> for i in range(len(s)):
>>>     if s[i] == "o":
>>>         counter += 1
		

Помним, что строки неизменяемы, поэтому подменить i-ый символ по индексу не получится, нужно создавать новый объект:

			>>> s[i] = "X"
Traceback (most recent call last):
File "", line 1, in 
TypeError: 'str' object does not support item assignment
>>> s[:i] + "X" + s[i+1:]
'HellX, world!'
		

Либо можно преобразовать строку в список, сделать обработку, а потом склеить список обратно в строку:

			>>> arr = list(s)
>>> "".join(arr)
'Hello, world!'
		

А форматирование строк?

Типичная жизненная необходимость — сформировать строку, подставив в неё результат работы программы. Начиная с Python 3.6, это можно делать при помощи f-строк:

			>>> f"Строка '{s}' содержит {len(s)} символов."
"Строка 'Hello, world!' содержит 13 символов."
		

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

			>>> "Строка '%s' содержит %d символов" % (s, len(s))
>>> "Строка '{}' содержит {} символов".format(s, len(s))
		

Технически можно было обойтись склейкой, но это менее элегантно, а еще придётся следить, чтобы все склеиваемые кусочки были строками. Не рекомендую:

			>>> "Строка '" + s + "' содержит " + str(len(s)) + " символов."
"Строка 'Hello, world!' содержит 13 символов."
		

Цель работодателя на собеседовании — убедиться что вы соображаете и что вы справитесь с реальными задачами. Однако погружение в реальные задачи занимает несколько недель, а время интервью ограничено. Поэтому вас ждут учебные задания, которые можно решить за 10-30 минут, а также вопросы на понимание того, как работает код. О них и поговорим в следующей части.

Следите за новыми постами
Следите за новыми постами по любимым темам
29К открытий29К показов