В статье рассматриваются решения задач, в которых отрабатываются навыки использования кортежей, списков, цикла FOR in range, цикла в цикле, методов split и join.
Лесенка чисел.
Дано натуральное число n≤9. Требуется вывести лесенку из n ступенек. Например: если n = 4, то вывод должен быть:
1
12
123
1234
Делаем цикл в цикле, второй цикл пишет числа с 1 до i первого цикла.
n = int(input())
for i in range(1, n+1):
....for ii in range(1, i+1):
........print(ii, end='')
....print()
Последний print нужен для переноса строки при выходе из второго цикла.
Замечательные числа ч.1.
Напишите программу, которая выведет все двузначные числа, которые равны удвоенному произведению своих цифр.
for i in range(10, 100):
....nm = str(i)
....if i == int(nm[0]) * int(nm[1]) * 2:
........print(i, end='')
В цикле переменную i переводим в строку nm, чтобы воспользоваться возможностями работы со списком и взять первый символ строки и второй. Ответом будет единственное число: 36.
Замечательные числа ч.2
Заданы два четырёхзначных числа A и B. Найдите все числа между A и B, являющихся палиндромами.
a = int(input())
b = int(input())
for i in range(a, b):
....ii = str(i)
....if int(i / 100) == int(ii[3] + ii[2]):
........print(i)
int(i / 100) - число из первых двух цифры, int(ii[3] + ii[2]) - число из четвертой и третьей цифр.
Флаги.
Программа должна по данному числу 1 <= n <= 9 вывести n флагов. Внутри каждого флага надо записать номер флага. Например при n=3:
+___ +___ +___
|1 / |2 / |3 /
|__\ |__\ |__\
|......|......|
Первая, третья и четвертые строки выводятся просто print*n, а чтобы во вторую строку вставлять номер, приходится делать цикл. Знак '\n' - это перенос строки.
n = int(input())
print('+___ ' * n)
b = ''
for i in range(1, n + 1):
....if i == n:
........b = '\n'
....print('|' + str(i) + ' / ', end=b)
print('|__\\ ' * n)
print('| ' * n)
Сумма факториалов.
Задано число n. Вычислите сумму 1!+2!+3!+...+n!. Должен быть использован только один цикл.
def fact(m):
....if m > 1:
........return m * fact(m - 1)
....else:
........return 1
n = int(input())
s = 0
for i in range(1, n + 1):
....s = s + fact(i)
print(s)
Для вычисления факториала любого числа делаем функцию fact, которая использует рекурсию. В цикле просто складываем результаты работы функции.
Потерянная карточка.
Вводится число карточек n. Затем вводятся номера n-1 карточек. Нужно найти номер недостающей (не введенной) карточки.
n = int(input())
s = n * (n + 1) / 2
si = 0
for i in range(1, n):
....ii = int(input())
....si = si + ii
print(int(s - si))
Задача интересна тем, что здесь применяется прием нахождения неизвестного номера, который основан на том, что неизвестный номер равен разности суммы всех номеров и суммы введенных номеров.
Сумма всех номеров s = n * (n + 1) / 2, сумма введенных - si = si + ii в цикле. Такой прием используется при нахождении номера промежуточного стержня в задаче "Ханойские башни" (эта задача описана в моей статье Рекурсия ч.2)
Ферзи.
На доске 8×8 стоят 8 ферзей. Вводятся координаты всех ферзей и нужно определить, есть ли среди них пара бьющих друг друга. Если ни одна пара ферзей не бьет друг друга, то выводится "NO".
f = []
hit = False
for i in range(8):
....f.append(list(map(int, input().split())))
for i in range(8):
....x1 = f[i][0]
....y1 = f[i][1]
........for ii in range(i+1, 8):
............x2 = f[ii][0]
............y2 = f[ii][1]
............if x1 == x2 or y1 == y2 or abs(y2 - y1) == abs(x2 - x1):
................hit = True
if hit:
....print('YES')
else:
....print('NO')
Все координаты вводятся в список f[(x1, y1), ..(x8, y8)]. Организуем цикл для каждого ферзя и внутри него еще цикл по всем ферзям, чтобы определить есть ли пары, которые бьют друг друга. Если x1 == x2 or y1 == y2 or abs(y2 - y1) == abs(x2 - x1), то ферзи бьют друг друга и признак hit= True.
Уникальные элементы.
Выведите уникальные элементы списка, то есть те, которые встречаются в списке только один раз.
a = list(map(int, input().split()))
b = []
den = []
for i in range(len(a)):
....if a[i] not in den:
........counter = 0
........for x in range(1, len(a) - i):
............if a[i] == a[i + x]:
................counter += 1
........if counter == 0:
............b.append(a[i])
........else:
............den.append(a[i])
print(*b)
Все уникальные элементы кладем в список b. Первый цикл идет по заданному списку, а второй цикл для каждого элемента ищет его дубль дальше по списку и если не находит, то добавляет его в b.
Сжатие списка.
Нужно “сжать” заданный список чисел, переместив все ненулевые числа в левую часть, а все нули - в правую часть списка. Задача должна быть решена за один проход по списку.
a = list(map(int, input().split()))
ii = 0
for i in range(len(a)):
....if a[ii] == 0:
........a.pop(ii)
........a.append(0)
....else:
........ii += 1
print(*a)
Здесь приходится использовать счетчик ii, независимый от списка a, так как список постоянно меняется. Если находим ноль, то его удаляем методом pop и добавляем в конец методом append. При это счетчик ii не наращивается, так как на место удаленного нуля встает следующий элемент списка.
Самое частое число.
Найдите в списке число, которое встречается чаще других.
a = list(map(int, input().split()))
c = 0
mc = 0
num = ''
for i in range(len(a)):
....x = a[i]
....c = 0
....for ii in range(len(a)):
........if x == a[ii]:
............c += 1
....if mc < c:
........mc = c
........num = x
print(num)
Делаем цикл в цикле и ищем для каждого числа сколько раз оно встречается в списке.
Заключение.
Другие примеры решения задач можно прочитать в моих статьях:
Желаю всем успехов в программировании!