2次元配列の下記の合計を求める方法を説明します。
なぜそうなるのかという仕組みも書いているので、理解したうえでコーディングが出来るようになります。
- 行
- 列
- 全要素
行の合計
map関数を使う方法
map関数を使って、各行の合計を求めます。
l = [[1, 0, 1], \ [1, 1, 1], \ [0, 0, 1]] #各行の合計 rowsSum = map(sum, l) print(next(rowsSum)) print(next(rowsSum)) print(next(rowsSum)) """出力 2 3 1 """
- map関数によって、lの全ての要素(l[0], l[1], l[2])に対してsum関数を実行し、各行の和を求めています。map関数の結果、イテレータを返しrowsSumに代入します。
- l[0]は[1, 0, 1]が入っています。
- next関数によってイテレータの各要素の取り出し、出力をしています。
ジェネレータ式を使う方法
ジェネレータ式を使って、各行の合計を求めます。
ジェネレータ式(generator expression)の詳細、ジェネレータとイテレータの違いについては下記をご確認ください。
・用語集 — Python 3.9.4 ドキュメント
・Difference between Python’s Generators and Iterators – Stack Overflow
l = [[1, 0, 1], \ [1, 1, 1], \ [0, 0, 1]] #各行の合計 rowsSum = (sum(row) for row in l) #ジェネレータ式 print(next(rowsSum)) print(next(rowsSum)) print(next(rowsSum)) """出力 2 3 1 """
- ジェネレータ式によって、下記を繰り返すことでジェネレータイテレータを生成し、rowsSumに代入しています。ここでは、ジェネレータイテレータはイテレータと同じです。
- lの要素を取り出し、rowに入れ、sum(row)の結果をジェネレータイテレータの要素とします。
- next関数によってイテレータの各要素の取り出し、出力をしています。
列の合計
リスト内包表記を使う方法
リスト内包表記を使って、各列の合計を求めます。
本方法では、各列の合計はリストとして出力されます。mapを使用する方法もありますが、各列の合計をリストとして扱いたい場合は本方法が有効です。
l = [[1, 0, 1], \ [1, 1, 1], \ [0, 0, 1]] #各列の合計 columnsSum = [sum(column) for column in zip(*l)] print(columnsSum) """出力 [2, 1, 3] """
- *lによって引数リストのアンパック(*1)をして、引数として各リスト(l[0], l[1], l[2])を渡します。
- zip関数は各リストのi番目の要素をi番目のタプルに入れ、タプルのイテレータを返します。
- 0番目のタプル生成例を示します。l[0]の0番目の要素である1, l[1]の0番目の要素である1, l[2]の0番目の要素である0が0番目のタプルに入ります。1番目、2番目のタプルも同様の考え方です。
- それぞれのタプルの中身です。0番目のタプル(1, 1, 0), 1番目のタプル(0, 1, 0), 2番目のタプル(1, 1, 1)
- sum(column)によって各タプルの要素を合計し、それぞれの結果をリストの要素にしています。
- columnsSumsに生成されたリストを代入しています。
(*1)4. その他の制御フローツール — Python 3.9.4 ドキュメント
mapを使う方法
mapを使って、各列の合計を求めます。
l = [[1, 0, 1], \ [1, 1, 1], \ [0, 0, 1]] #各列の合計 columnsSum = map(sum, zip(*l)) print(next(columnsSum)) print(next(columnsSum)) print(next(columnsSum)) """出力 2 1 3 """
- zip(*l)の説明は、リスト内包表記を使う方法と同じです。
- map(sum, zip(*l))では、zip(*l)で生成されるタプルのイテレータの各タプルに対してsum関数を実行します。
- columnsSumsにmap関数の結果であるイテレータを代入しています。
全要素の合計
行の合計に対してsum関数を使用することで、全要素の合計が求められます。
l = [[1, 0, 1], \ [1, 1, 1], \ [0, 0, 1]] #mapを使う方法 allSum1 = sum(map(sum, l)) print(allSum1) """出力 6 """ #ジェネレータ式を使う方法 allSum2 = sum(sum(row) for row in l) print(allSum2) """出力 6 """
参考
python – How do I sum the columns in 2D list? – Stack Overflow
列の合計の参考です。
How would I sum a multi-dimensional array in the most succinct python? – Stack Overflow
全要素の合計の参考です。
6. 式 (expression) — Python 3.9.4 ドキュメント
イテラブルのアンパックの参考です。
コメント