Step 13 (S-14684)

From Stepik Wiki
Jump to: navigation, search

Step on Stepik: https://stepik.org/lesson/3368/step/13

Давайте рассмотрим, как можно инициализировать двумерные списки на примере генерации квадратной матрицы n на n, состоящий из одних нулей. Как сгенерировать такую матрицу? Мы умеем генерировать линейный список состоящий из одних нулей.

S-14684-1.png

Для того, чтобы получить список из n списков, состоящих из n нулей, попробуем полученный список умножить на n.

S-14684-2.png

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

S-14684-3.png

Это явно не тот результат, что мы хотели получить. Изменились все вложенные списки. Это произошло потому, что мы достаточно специфичным образом генерировали нашу матрицу. Вначале мы создали список состоящий из нулей. Затем нами был создан список, состоящий n ссылок на полученный ранее список. Каждый элемент списка а, это ссылка на один и тот же объект. Именно поэтому, когда мы изменяем элемент вложенного списка, это отражается на всех элементах списка а.

Для того чтобы создать "настоящую" матрицу нужно использовать генераторы списков (list comprehension).

S-14684-4.png

Для каждого i, принимающего значения от 0 до n - 1, мы заново генерируем список, состоящий из n нулей: [0] * n. Такая конструкция создаст нам список из n различных списков (каждый из этих списков является отдельным объектом). И изменение элемента внутри одного из этих списков, никак не повлияет на остальные.

Можно использовать вложенные конструкции генераторов списков:

S-14684-5.png

Мы n раз запускаем генерацию списка: [0 for j in range(n)], результатом будет матрица n на n.