Python
 Computer >> コンピューター >  >> プログラミング >> Python

【Python】itertools.groupbyでリスト要素の連続範囲インデックスをグループ化して取得する方法

Pythonでリスト内の要素が連続している範囲のインデックスをグループ化して取得したい場合、defaultdictを活用するのが便利です。シンプルなループ処理に加え、標準ライブラリのgroupbyメソッドやlenメソッド、listメソッド、appendメソッドを組み合わせることで実現できます。

サンプルコード

以下に具体的な実装例を示します。

from itertools import groupby
from collections import defaultdict

my_list = [63, 12, 84, 91, 52, 39, 25, 27, 20, 11, 0, 9]

print("元のリスト : ")
print(my_list)

my_index = 0
my_result = defaultdict(list)

for key, sub in groupby(my_list):
   element = len(list(sub))
   my_result[key].append((my_index, my_index + element - 1))
   my_index += element

print("結果の辞書 : ")
print(my_result)

実行結果

元のリスト :
[63, 12, 84, 91, 52, 39, 25, 27, 20, 11, 0, 9]
結果の辞書 :
defaultdict(<class 'list'>, {63: [(0, 0)], 12: [(1, 1)], 84: [(2, 2)], 91: [(3, 3)], 52: [(4, 4)], 39: [(5, 5)], 25: [(6, 6)], 27: [(7, 7)], 20: [(8, 8)], 11: [(9, 9)], 0: [(10, 10)], 9: [(11, 11)]})

処理の流れと解説

  • まず、必要なパッケージであるitertools.groupbycollections.defaultdictをインポートします。

  • 整数値を格納したリストを定義し、コンソールに表示します。

  • 現在のインデックス位置を追跡するための変数を0で初期化します。

  • キーごとにリストを自動生成できるdefaultdictを作成します。これにより、存在しないキーにアクセスしてもエラーが発生しません。

  • groupbyメソッドを使ってリストを走査し、隣接する同じ値の要素をグループ化します。

  • 各グループの長さをlen(list(sub))で取得し、開始インデックスと終了インデックスのタプルとして辞書に追加します。

  • グループの要素数だけインデックスを進め、次のグループの開始位置を正しく計算できるようにします。

  • 最終的に、各要素をキーとし、その連続範囲(開始インデックス、終了インデックス)を値とする辞書が出力されます。

ポイント

この手法は、リスト内に同じ値が連続して出現するケースで特に有効です。例えば、データの圧縮やランレングスエンコーディングのような処理にも応用できます。groupbyは隣接する同一要素のみをまとめるため、離れた位置にある同じ値は別々のグループとして扱われる点に注意してください。

  1. Pythonで別のリストをインデックスにしてリストの要素を取得する3つの方法

    Pythonでは、あるリストの要素を、別のリストに格納された数値(インデックス位置)に基づいて取り出したい場面がよくあります。例えば、曜日名が入ったリストから、指定された位置の要素だけを抜き出すようなケースです。本記事では、この処理を実現する3つの方法を、具体的なコード例とともに解説します。 mapと__getitem__を組み合わせる方法 リストには特殊メソッド(マジックメソッド)である__getitem__が用意されており、これを使うとリストの要素へアクセスできます。このメソッドをmap関数と組み合わせることで、2つ目のリストの各要素をインデックスとして扱い、1つ目のリストから対応する要

  2. Pythonでリストから指定したインデックスの複数要素を削除する方法

    Pythonのリストから単一の要素を削除するのは、del文とインデックスを組み合わせれば簡単に行えます。しかし、複数のインデックスに該当する要素をまとめて削除したいケースでは、少し工夫が必要です。本記事では、削除対象となるインデックスのリストを指定して、元のリストから該当する要素だけを取り除く方法を2つ紹介します。方法1:sorted()とdelを組み合わせるこのアプローチでは、まず削除したい位置(インデックス)を格納したリストを作成します。その後、降順にソートしてから後ろの要素から順に削除することで、削除処理中にインデックスがずれる問題を回避し、元のリストの構造を保ったまま安全に要素を削除で