Python でリストをフラット化する方法

Aliaksei Yursha 2023年1月30日
  1. Python リストの浅い平坦化
  2. Python リストの深い平坦化
Python でリストをフラット化する方法

平坦化は、ネストされたリストのリストを取得し、ネストされたリストを含まない別のデータ構造に変換する操作です。
代わりに、最初にネストされたすべてのリストのすべての要素が含まれます。
このようなデータ構造は、フラットまたはフラット化リストと呼ばれます。

元のリストには、ネストの最初のレベルのネストされたリストのみを含めることができます。
[[1、2]、[3、4]]
それ以外の場合、ネストの 2 番目、3 番目、およびそれ以上のレベルのリストが含まれます。
例えば、[[[1], [2]], [3、4]]
このようなリストには、深くネストされたリストが含まれると言われています。

ネストの 1つのレベルだけをネスト解除する場合は、shallow flattening と呼びます。
ネストネスのすべてのレベルのネストを解除する場合は、フラット化と呼ばれます。

Python リストの浅い平坦化

理解して視覚化する簡単なアプローチは、二重の for ループを使用することです。

最初の for ループはネストされたリストを横断します。2 番目の for ループは、ネストされた各リストの要素を繰り返し処理し、それらを結果のフラットリストに 1つずつ追加します。

>>> flat_list = []
>>> original_list = [[1, 2], [3, 4]]
>>> for l in original_list:
...   for item in l:
...     flat_list.append(item)
...
>>> flat_list
[1, 2, 3, 4]

上記のメソッドは明確で読みやすいですが、Python の表現力により、
同じ目標をたった 1 行で達成します。
Python のリスト内包表記が役立ちます。

>>> original_list = [[1, 2], [3, 4]]
>>> flat_list = [item for l in original_list for item in l]
>>> flat_list
[1, 2, 3, 4]

フラットリスト自体は必要ないが、すべての要素を繰り返し処理できるようにする場合
すべてのサブリストが単一のフラットなデータ構造から来ているかのように、itertools.chain() を使用できます。

>>> import itertools
>>> original_list = [[1, 2], [3, 4]] 
>>> iterator = itertools.chain(*original_list)
>>> for item in iterator:
...   print(item)
...
1
2
3
4

Pandas(Python でのデータ分析用のオープンソースパッケージ)を使用する場合、組み込みの方法もあります。

>>> from pandas.core.common import flatten
>>> original_list = [[1, 2], [3, 4]]  
>>> flat_list = list(flatten(original_list))
>>> flat_list
[1, 2, 3, 4]

Python リストの深い平坦化

上記のように、リストを深くネストしている場合、浅い平坦化は機能しません。
以下の例に示すように、ネストの最初のレベルだけをネスト解除します。

>>> deeply_nested_list = [[[1, 2], 3], [4, 5, 6]]
>>> flat_list = [item for l in deeply_nested_list for item in l]
>>> flat_list
[[1, 2], 3, 4, 5, 6]

深いフラット化を行うには、iteration-utilitiesPyPI パッケージの iteration_utilities.deepflatten() を使用します。

まず、PyPI パッケージ自体をインストールします。

$ pip install iteration-utilities

次に、深くネストされたリストをフラット化します。

>>> from iteration_utilities import deepflatten
>>> deeply_nested_list = [[[1, 2], 3], [4, 5, 6]]
>>> flat_list = list(deepflatten(deeply_nested_list))
>>> flat_list
[1, 2, 3, 4, 5, 6]

関連記事 - Python List