Python Numpy無しで転置行列を作る
data = [ [1, 2, 3], [4, 5, 6], [7, 8, 9], [0, 1, 2] ]
これを
data = [ [1, 4, 7, 0], [2, 5, 8, 1], [3, 6, 9, 2] ]
こうしたい時。
結論から書くと
list(map(list, zip(*data)))
これでOK。
まず、zip関数は
それぞれのイテラブルから要素を集めたイテレータを作ります。
この関数はタプルのイテレータを返し、その i 番目のタプルは引数シーケンスまたはイテラブルそれぞれの i 番目の要素を含みます。このイテレータは、入力のイテラブルの中で最短のものが尽きたときに止まります。単一のイテラブル引数が与えられたときは、 1-タプルのイテレータを返します。引数がなければ、空のイテレータを返します。次と等価です:
(ドキュメントより)
つまり、
x = [1, 2, 3] y = [4, 5, 6] zipped = zip(x, y) list(zipped) """ zipped = [(1, 4), (2, 5), (3, 6)] """
となる。ただし、zip関数が返すのはイテレータのため、リストとして扱いたいときにはlist関数を使う必要がある。
また、イテラブルオブジェクトである引数の先頭に*をつけて指定すると、
引数は呼び出しの時に展開されて渡される。
なので、
zip(*data)
は、
zip([1, 2, 3], [4, 5, 6], [7, 8, 9], [0, 1, 2])
と同じ。
なので、
zipped = zip(*data) list(zipped) """ zipped = [ (1, 4, 7, 0), (2, 5, 8, 1), (3, 6, 9, 2) ] """
となる。
ただ、各要素はタプルなので、それぞれをリストにしたい場合は、
map関数を使い、各要素をlistへ変換する。
これを組み合わせると、
list(map(list, zip(*data)))
という書き方で転置行列ができるということになる。