Python講座 / 集合で重複を除き、コレクションを選ぶ

集合はハッシュ可能な要素を重複なく保持し、所属の確認や集合演算に使えます。集合へ変換すると重複の回数や位置の情報が失われるため、取り除いてよい情報かを先に判断します。

集合の作成と演算を読む

空でない集合は{"food", "books"}のように書き、空の集合はset()で作ります。空の波かっこ{}は辞書です。リストや辞書はハッシュ可能ではないため、集合の要素にはできません。集合の反復順を意味のある表示順やインデックスの代わりに使わないでください。

式 意味
a | b 和集合
a & b 共通部分
a - b aだけにある要素
a ^ b 片方だけにある要素

キーによる識別と重複検証は、辞書でキーと値を管理すると実習:CSVを検証して集計レポートを作るで扱う規則とつながります。

使用カテゴリと許可カテゴリを比較する

sets.pyへ全体コードを保存し、仮想環境でpython sets.pyを実行します。

used = {"food", "transport", "food"}
allowed = {"food", "books"}
print(sorted(used))
print(sorted(used & allowed))
print(sorted(used - allowed))
used.discard("missing")
print("food" in used)

出力を比較できるようにsorted()で整列して表示しています。

['food', 'transport']
['food']
['transport']
True

重複削除と差集合の意味を確認する

重複したfoodは一つの要素になります。used - allowedには許可されていないtransportが残り、共通部分にはfoodが残ります。sorted()の結果は整列したリストであり、元の集合そのものに順番を与えるわけではありません。

ハッシュ可能な要素ならlist(dict.fromkeys(items))で最初の出現順を保ちながら重複を除く方法もあります。ただし、消した各出現が別の取引や記録を表していなかったかを考える必要があります。重複を削ることと、正しいデータか確認することは別です。

存在しない要素と情報の保持を考える

remove()は要素がなければKeyErrorになりますが、discard()は存在しなくても失敗しません。必須要素の欠落を見つけたいのか、任意の片付けをしたいのかで選びます。

foodを再追加して要素数が変わらないことを確認し、booksをusedへ足して共通部分を比較したら、元へ戻します。同じ金額の支出が二回あっても別の取引かもしれません。金額を集合にして合計すると、その取引を一つ失います。

順序と重複にはリスト、短い位置付きレコードにはタプル、名前による検索には辞書、重複のない所属確認には集合を選びます。扱いやすさだけでなく、必要な情報を残せる構造かを判断してください。

同額の支払いが二つあっても、別々の取引かもしれません。値の重複除去と取引IDの重複検証は区別します。8,000の支払いをsetで一つにまとめると合計が変わります。取引IDを確認し、同じIDを拒否するか更新するかを業務ルールとして決めます。

関連する公式リファレンス