

ソースコードは次の通りです。

[code]

    mt = [[None]*9]*9
    for i in range(9):
        for j in range(9):
            mt[i][j] = (i+1) * (j+1)
            print("%2d " % (mt[i][j]), end=" ")
        print()
    
    print(mt) # why
    for i in range(9):
        for j in range(9):
            print("%2d " % (mt[i][j]), end=" ")
        print()
    
[/code]

実行結果はなぜか次のようになってしまいます。

[code]

     1   2   3   4   5   6   7   8   9  
     2   4   6   8  10  12  14  16  18  
     3   6   9  12  15  18  21  24  27  
     4   8  12  16  20  24  28  32  36  
     5  10  15  20  25  30  35  40  45  
     6  12  18  24  30  36  42  48  54  
     7  14  21  28  35  42  49  56  63  
     8  16  24  32  40  48  56  64  72  
     9  18  27  36  45  54  63  72  81  
    [[9, 18, 27, 36, 45, 54, 63, 72, 81], [9, 18, 27, 36, 45, 54, 63, 72, 81], [9, 18, 27, 36, 45, 54, 63, 72, 81], [9, 18, 27, 36, 45, 54, 63, 72, 81], [9, 18, 27, 36, 45, 54, 63, 72, 81], [9, 18, 27, 36, 45, 54, 63, 72, 81], [9, 18, 27, 36, 45, 54, 63, 72, 81], [9, 18, 27, 36, 45, 54, 63, 72, 81], [9, 18, 27, 36, 45, 54, 63, 72, 81]]
     9  18  27  36  45  54  63  72  81  
     9  18  27  36  45  54  63  72  81  
     9  18  27  36  45  54  63  72  81  
     9  18  27  36  45  54  63  72  81  
     9  18  27  36  45  54  63  72  81  
     9  18  27  36  45  54  63  72  81  
     9  18  27  36  45  54  63  72  81  
     9  18  27  36  45  54  63  72  81  
     9  18  27  36  45  54  63  72  81  
    
[/code]

原因が分からずに困っています。  
よろしくお願い申し上げます。


CC BY-SA 4.0
2020-10-29T05:42:10.867
71580
2020-10-29T06:16:57.403
2020-10-29T05:51:02.827
3475
42524
question
python
python（ver.3.9）で９ｘ９の2次元配列（リスト）を作って， そこに九九の表を格納し， 格納後，表示したいのですが妙な結果が得られます。


`mt = [[None]*9]*9` を  
`mt = [[None] * 9 for i in range(9)]` に変えれば直ります。

ご質問の結果となるのは[多次元配列の罠](https://note.nkmk.me/python-list-initialize/)です。  
リンク先が詳細を記述していますが、`[None]*9`というリストをその外側で9個コピーしているため、 **内部リストの実体は同一** です。

そのため、`mt[i]`を書き換えるたびに`mt[0]`から`mt[8]`まで全ての実体が影響を受けて、例えば下記のコードのように1の段の配列(`mt[0]`のリスト)も書き換わってしまいます。

[code]

    mt = [[None]*9]*9
    #mt = [[None] * 9 for i in range(9)]
    for i in range(9):
        for j in range(9):
            mt[i][j] = (i+1) * (j+1)
            print("%2d " % (mt[i][j]), end=" ")
        print("1の段の配列 = %s" % mt[0])
    
[/code]

出力結果:

[code]

     1   2   3   4   5   6   7   8   9  1の段の配列 = [1, 2, 3, 4, 5, 6, 7, 8, 9]
     2   4   6   8  10  12  14  16  18  1の段の配列 = [2, 4, 6, 8, 10, 12, 14, 16, 18]
     3   6   9  12  15  18  21  24  27  1の段の配列 = [3, 6, 9, 12, 15, 18, 21, 24, 27]
     4   8  12  16  20  24  28  32  36  1の段の配列 = [4, 8, 12, 16, 20, 24, 28, 32, 36]
     5  10  15  20  25  30  35  40  45  1の段の配列 = [5, 10, 15, 20, 25, 30, 35, 40, 45]
     6  12  18  24  30  36  42  48  54  1の段の配列 = [6, 12, 18, 24, 30, 36, 42, 48, 54]
     7  14  21  28  35  42  49  56  63  1の段の配列 = [7, 14, 21, 28, 35, 42, 49, 56, 63]
     8  16  24  32  40  48  56  64  72  1の段の配列 = [8, 16, 24, 32, 40, 48, 56, 64, 72]
     9  18  27  36  45  54  63  72  81  1の段の配列 = [9, 18, 27, 36, 45, 54, 63, 72, 81]
    
[/code]


CC BY-SA 4.0
2020-10-29T06:16:57.403
71581
2020-10-29T06:16:57.403
9820
71580
answer