Почему в этом списке python хранятся только последние элементы ввода - PullRequest
0 голосов
/ 26 мая 2020

Пожалуйста, объясните следующее поведение

import sys
input=sys.stdin.readline

for _ in range(int(input())):
    n=int(input())
    m=int(input())
    vertices=[[0, 0]]*n
    edges=[[0, 0, 0]]*m
    for i in range(m):
        edges[i][0], edges[i][1], edges[i][2]=list(map(int, input().split()))
    for i in range(m):
        print(edges[i][0], edges[i][1], edges[i][2])

Когда в программу вводится следующий ввод:

1
5
7
1 2 1
2 3 2
2 4 6
5 2 1
5 1 3
4 5 2
3 4 3

Создается этот вывод:

3 4 3
3 4 3
3 4 3
3 4 3
3 4 3
3 4 3
3 4 3

Почему во всех элементах сохраняются только последние входные данные?

1 Ответ

1 голос
/ 30 мая 2020

Давайте посмотрим на этот сеанс интерпретатора:

>>> a = [[0,0,0]] * 5
>>> a
[[0, 0, 0], [0, 0, 0], [0, 0, 0], [0, 0, 0], [0, 0, 0]]
>>> a[0][0] = 1
>>> a
[[1, 0, 0], [1, 0, 0], [1, 0, 0], [1, 0, 0], [1, 0, 0]]

На самом деле это обычная ошибка в Python. Код переводится примерно так:

inner = [0, 0, 0]
a = [inner, inner, inner, inner, inner]

Такой способ записи делает более понятным, что вы фактически создаете список, где все записи указывают на один и тот же объект (inner) .

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

vertices=[[0, 0] for _ in range(n)]
edges=[[0, 0, 0] for _ in range(m)]

Другое исправление - использование numpy и объявление 2D-матрица с использованием numpy.zeros(n, 2). Numpy обычно используется в приложениях, интенсивно использующих математику / числа.

...