Наполнение матрицы с тремя параметрами n, m и value

По следам этого вопроса. Не могли бы вы пояснить как работает этот механизм:

for i in range(n):            # тут я понимаю что i принимает значение n
    matrix.append([])          # с этим все понятно, добавляем пустой список как по условию.
    for j in range(m):      # вот затык, поясните пожалуйста какое волшебство тут?
        matrix[i].append(value)

Заранее благодарен.


Ответы (1 шт):

Автор решения: CrazyElf

Тонкость тут на самом деле немного другая, чем обсуждается. Вернее, их несколько. Поясню комментариями и ниже текстом:

for i in range(n):              # i принимает значения от 0 до n-1
    matrix.append([])           # добавляем пустой список на каждой итерации по i
    for j in range(m):          # j принимает значения от 0 до m-1
        matrix[i].append(value) # value добавляем в добавленный выше список

Пояснения:

  • range с одним параметром при переборе выдаёт числа от 0 до указанного параметра - 1
  • переменная цикла j тут не используется, в этом случае обычно вместо переменной указывают _ либо используют другие способы генерации списков
  • когда идёт обращение к matrix[i] так получается чудесным образом, что это тот самый элемент matrix, который был добавлен выше через matrix.append([]), это не самый лучший способ, лучше всё-таки делать такие вещи в явном виде, а не полагаться на такие совпадения

Ну то есть лучше было бы сделать так:

for i in range(n):
    item = []
    for _ in range(m):
        item.append(value)
    matrix.append(item)

А если value при этом неизменяемый тип, то можно и так:

for i in range(n):
    matrix.append([value]*m)

Или, ещё такие способы с помощью "списковых сокращений":

# для изменяемого value
matrix = [[value for _ in range(m)] for _ in range(n)]

# для неизменяемого value
matrix = [[value]*m for _ in range(n)]

Мне кажется последние способы даже и понятнее должны быть, если разобраться.

P.S. Про неизменяемость я что-то не совсем то написал, ответ нуждается в переделке :/

→ Ссылка