1. Реверс строки без использования встроенных функций
Задача: Напишите функцию, которая реверсирует строку без использования срезов или встроенных функций.
Решение:
def reverse_string(s):
reversed_str = ""
for char in s:
reversed_str = char + reversed_str # Добавляем символ в начало строки
return reversed_str
# Пример использования
print(reverse_string("Python")) # Вывод: "nohtyP"
Комментарий: Мы итерируем по строке и добавляем каждый символ в начало новой строки, тем самым инвертируя её.
2. Проверка на палиндром
Задача: Напишите функцию, которая проверяет, является ли строка палиндромом (читается одинаково слева направо и справа налево).
Решение:
def is_palindrome(s):
return s == s[::-1]
# Пример использования
print(is_palindrome("racecar")) # Вывод: True
Комментарий: Используем срез для реверсирования строки и сравниваем её с оригиналом.
3. Подсчёт вхождений элемента в списке
Задача: Напишите функцию, которая подсчитывает количество вхождений элемента в списке.
Решение:
def count_occurrences(lst, value):
count = 0
for item in lst:
if item == value:
count += 1
return count
# Пример использования
print(count_occurrences([1, 2, 3, 1, 1], 1)) # Вывод: 3
Комментарий: Итерируем по списку и увеличиваем счётчик при нахождении совпадения.
4. Уникальные элементы списка
Задача: Напишите функцию, которая возвращает список уникальных элементов из исходного списка.
Решение:
def unique_elements(lst):
return list(set(lst))
# Пример использования
print(unique_elements([1, 2, 2, 3, 4, 4])) # Вывод: [1, 2, 3, 4]
Комментарий: Используем множество для удаления дубликатов, так как множества не содержат повторяющихся элементов.
5. Сортировка списка без использования встроенных функций
Задача: Напишите функцию, которая сортирует список чисел по возрастанию без использования встроенных функций сортировки.
Решение:
def bubble_sort(lst):
n = len(lst)
for i in range(n):
for j in range(0, n-i-1):
if lst[j] > lst[j+1]:
lst[j], lst[j+1] = lst[j+1], lst[j]
return lst
# Пример использования
print(bubble_sort([64, 34, 25, 12, 22, 11, 90])) # Вывод: [11, 12, 22, 25, 34, 64, 90]
Комментарий: Реализуем сортировку пузырьком, сравнивая и меняя местами соседние элементы.
6. Вычисление факториала рекурсивно
Задача: Напишите рекурсивную функцию для вычисления факториала числа.
Решение:
def factorial(n):
if n == 0:
return 1
else:
return n * factorial(n-1)
# Пример использования
print(factorial(5)) # Вывод: 120
Комментарий: Базовый случай — факториал 0 равен 1. Рекурсивно умножаем число на факториал предыдущего.
7. Генератор чисел Фибоначчи
Задача: Напишите генератор, который возвращает числа Фибоначчи.
Решение:
def fibonacci_generator():
a, b = 0, 1
while True:
yield a
a, b = b, a + b
# Пример использования
gen = fibonacci_generator()
for _ in range(10):
print(next(gen), end=" ") # Вывод: 0 1 1 2 3 5 8 13 21 34
Комментарий: Используем yield для создания бесконечного генератора чисел Фибоначчи.
8. Поиск второго по величине числа в списке
Задача: Напишите функцию, которая находит второе по величине число в списке.
Решение:
def second_largest(lst):
unique_lst = list(set(lst)) # Убираем дубликаты
unique_lst.sort()
return unique_lst[-2] if len(unique_lst) > 1 else None
# Пример использования
print(second_largest([1, 2, 3, 4, 5])) # Вывод: 4
Комментарий: Убираем дубликаты, сортируем список и возвращаем предпоследний элемент.
9. Проверка сбалансированности скобок
Задача: Напишите функцию, которая проверяет, правильно ли расставлены скобки в строке.
Решение:
def is_balanced(s):
stack = []
matching_brackets = {')': '(', '}': '{', ']': '['}
for char in s:
if char in matching_brackets.values():
stack.append(char)
elif char in matching_brackets:
if not stack or stack.pop() != matching_brackets[char]:
return False
return not stack
# Пример использования
print(is_balanced("({[()]})")) # Вывод: True
Комментарий: Используем стек для отслеживания открывающихся скобок и проверяем соответствие закрывающих.
10. Подсчёт частоты символов в строке
Задача: Напишите функцию, которая подсчитывает частоту каждого символа в строке.
Решение:
from collections import Counter
def char_frequency(s):
return dict(Counter(s))
# Пример использования
print(char_frequency("hello")) # Вывод: {'h': 1, 'e': 1, 'l': 2, 'o': 1}
Комментарий: Используем Counter из модуля collections для подсчёта частоты символов.
Продолжаем 👇
11. ✅ Проверка на анаграмму
Задача: Проверить, являются ли две строки анаграммами (содержат одинаковые буквы в разном порядке).
Решение:
def is_anagram(s1, s2):
return sorted(s1) == sorted(s2)
# Пример использования
print(is_anagram("listen", "silent")) # Вывод: True
Комментарий: Просто сортируем обе строки и сравниваем — если в них одинаковые буквы, отсортированные списки совпадут.
12. 🧠 Поиск всех пар с заданной суммой
Задача: Найти все пары чисел в списке, которые в сумме дают заданное число.
def find_pairs(lst, target):
seen = set()
pairs = set()
for num in lst:
diff = target - num
if diff in seen:
pairs.add((min(num, diff), max(num, diff))) # упорядочим пары
seen.add(num)
return list(pairs)
# Пример использования
print(find_pairs([1, 2, 3, 4, 5], 6)) # Вывод: [(1, 5), (2, 4)]
Комментарий: Используем множество для запоминания уже просмотренных чисел. Пары сохраняем в виде кортежей (упорядоченных), чтобы избежать дубликатов.
13. 📐 Нахождение самого длинного слова в строке
Задача: Вернуть самое длинное слово из строки.
def longest_word(s):
words = s.split()
return max(words, key=len)
# Пример использования
print(longest_word("I love programming in Python")) # Вывод: "programming"
Комментарий: Разбиваем строку по пробелам и ищем максимум по длине.
14. 🔁 Рекурсивный вывод чисел от N до 0
def countdown(n):
if n < 0:
return
print(n)
countdown(n - 1)
# Пример использования
countdown(5)
Комментарий: Классический пример рекурсии, просто уменьшаем n до тех пор, пока не достигнем отрицательного числа.
15. 📊 Группировка слов по анаграммам
Задача: Из списка слов сгруппировать слова, являющиеся анаграммами.
from collections import defaultdict
def group_anagrams(words):
result = defaultdict(list)
for word in words:
key = ''.join(sorted(word)) # сортируем слово, чтобы сравнить
result[key].append(word)
return list(result.values())
# Пример использования
print(group_anagrams(["eat", "tea", "tan", "ate", "nat", "bat"]))
# Вывод: [['eat', 'tea', 'ate'], ['tan', 'nat'], ['bat']]
Комментарий: Используем отсортированное слово как ключ, чтобы сгруппировать все его перестановки.
16. 🎛️ Перестановки строки (рекурсивно)
def permutations(s):
if len(s) <= 1:
return [s]
result = []
for i, char in enumerate(s):
for perm in permutations(s[:i] + s[i+1:]):
result.append(char + perm)
return result
# Пример использования
print(permutations("abc"))
# Вывод: ['abc', 'acb', 'bac', 'bca', 'cab', 'cba']
Комментарий: Классическая задача на рекурсию — разбиваем строку, фиксируем символ и вызываем перестановки от оставшихся.
17. 🧮 Быстрое возведение в степень (без **)
def power(a, b):
if b == 0:
return 1
half = power(a, b // 2)
return half * half if b % 2 == 0 else a * half * half
# Пример использования
print(power(2, 10)) # Вывод: 1024
Комментарий: Используем «разделяй и властвуй» для сокращения количества умножений до O(log b).
18. 🧪 Проверка на простое число
def is_prime(n):
if n <= 1:
return False
for i in range(2, int(n**0.5)+1):
if n % i == 0:
return False
return True
# Пример использования
print(is_prime(29)) # Вывод: True
Комментарий: Проверка до √n — минимально необходимый набор делений, чтобы определить простоту числа.
19. 🔁 Поиск самого длинного подстрочного палиндрома
def longest_palindrome(s):
result = ""
for i in range(len(s)):
for j in range(i, len(s)):
temp = s[i:j+1]
if temp == temp[::-1] and len(temp) > len(result):
result = temp
return result
# Пример использования
print(longest_palindrome("babad")) # Вывод: "bab" или "aba"
Комментарий: Перебираем все подстроки и проверяем, палиндром ли они. Неэффективно, но работает.
20. 💡 LRU Cache (на собеседованиях любят)
from collections import OrderedDict
class LRUCache:
def __init__(self, capacity):
self.cache = OrderedDict()
self.capacity = capacity
def get(self, key):
if key not in self.cache:
return -1
self.cache.move_to_end(key) # Обновляем "последнее использование"
return self.cache[key]
def put(self, key, value):
if key in self.cache:
self.cache.move_to_end(key)
self.cache[key] = value
if len(self.cache) > self.capacity:
self.cache.popitem(last=False) # Удаляем самый старый элемент
# Пример использования
lru = LRUCache(2)
lru.put(1, 1)
lru.put(2, 2)
print(lru.get(1)) # Вывод: 1
lru.put(3, 3)
print(lru.get(2)) # Вывод: -1, т.к. он удалён из-за лимита
Комментарий: Используем OrderedDict, который сохраняет порядок вставки и позволяет эффективно удалять старейшие элементы.