Counterクラスは要素をキーとして保存し、そのカウントを値として保存します。
本記事では、Counterクラスを使うための準備、初期化、カウントする方法等のCounterクラスの基本的な使い方を説明します。また、辞書との比較もしているため、Counterクラスの使いやすさがわかると思います。
準備
collectionsモジュールまたは、Counterクラスをimportする必要があります。
collectionsモジュールをimportする方法
from collections import Counter c = Counter("apple") print(c) """出力 Counter({'p': 2, 'a': 1, 'l': 1, 'e': 1}) """
Counterクラスをimportする方法
import collections c = collections.Counter("apple") print(c) """出力 Counter({'p': 2, 'a': 1, 'l': 1, 'e': 1}) ""
初期化
初期期は、下記の方法があります。
from collections import Counter #空のカウンター c = Counter() print(c) """出力 Counter() """ #イテラブル(文字列、辞書、リスト) #文字列 c = Counter("apple") print(c) """出力 Counter({'p': 2, 'a': 1, 'l': 1, 'e': 1}) """ #辞書 d = {"apple":1, "banana":2} print(Counter(d)) """出力 Counter({'banana': 2, 'apple': 1}) """ #リスト l = ["apple", "banana", "apple", "apple", "banana", "apple", "banana" ] c = Counter(l) print(c) """出力 Counter({'apple': 4, 'banana': 3}) """ #キーワード引数 c = Counter(apple=3, banana=4) print(c) """出力 Counter({'banana': 4, 'apple': 3}) """
メソッド
most_common
most_commonメソッドはCounterオブジェクト内の要素を出現回数の多い順にタプルのリスト形式で出力します。
from collections import Counter l = ["a", "a", "c", "b", "b", "a"] c = Counter(l) #①:引数を省略した場合、Counterオブジェクト内の全ての要素(タプルのリスト)が出力されます。 print(c.most_common()) """出力 [('a', 3), ('b', 2), ('c', 1)] """ #②:入力した引数個のCounterオブジェクトの要素が出力されます。 print(c.most_common(2)) """出力 [('a', 3), ('b', 2)] """ tplist = c.most_common() #③:リストなので下記の方法で逆順にできます print(tplist[::-1]) """出力 [('c', 1), ('b', 2), ('a', 3)] """ #④:タプルのリストなので下記の方法で各要素にアクセスできます。 print(tplist[0]) print(tplist[1]) print(tplist[2]) print(tplist[0][0]) print(tplist[0][1]) """出力 ('a', 3) ('b', 2) ('c', 1) a 3 """
イディオム
要素の出現回数をカウント
from collections import Counter l = ["a", "a", "c", "b", "b"] #① c1 = Counter(l) print(c1) """出力 Counter({'a': 2, 'b': 2, 'c': 1}) """ #② c2 = Counter() for i in range(len(l)): c2[l[i]] += 1 #特定の条件の時に任意の処理 if c2["b"] == 2: print(i) print(c2) """出力 4 Counter({'a': 2, 'b': 2, 'c': 1}) """
#①:出現回数をカウントする対象のオブジェクトが既に存在している場合
- Counter(l)の様に引数として渡すだけで要素の出現回数をカウントできます。
#②:オブジェクトの各要素を一つ一つカウントする場合
- カウントが特定の条件の場合に、任意の処理をする時に有効な方法です。
要素を削除
要素を取り除くためには、delを使う必要があります。
from collections import Counter l = ["a", "a", "c", "b", "b"] c = Counter(l) c["a"] -= 2 print(c) """出力 Counter({'b': 2, 'c': 1, 'a': 0}) """ del c["a"] print(c) """出力 Counter({'b': 2, 'c': 1}) """
カウントが0になっても要素は削除されません。del c[“a”]の様に、要素を指定して削除する必要があります。
値の合計
from collections import Counter l = ["a", "b", "b", "c", "c", "c"] c = Counter(l) total = sum(c.values()) print(c) print(total) """出力 Counter({'c': 3, 'b': 2, 'a': 1}) 6 """
値は、3, 2, 1なので、その合計の6が出力されています。
キーと値の積の合計
from collections import Counter l = [1, 2, 2, 3, 3, 3] c = Counter(l) total = sum([k*v for k, v in c.items()]) print(c) print(total) """出力 Counter({3: 3, 2: 2, 1: 1}) 14 """
total = sum([k*v for k, v in c.items()])の説明:
- c.items()により、(key, value)の組が出力されます。
- for k, v in c.items()では、タプルのアンパックにより、kにkeyがvにvalueが代入されます。
- [k*v for k, v in c.items()]により、k*vを要素とするリストを作成しています。※リスト内包表記
辞書との比較
辞書でも要素の出現回数をカウントすることが可能ですがCounterと比較した場合に幾つかのデメリットがあります。辞書を使う方法はモジュールのimportが不要な点は良いですが、Counterと同じことをする時のコーディング量が増えてしまいます。
存在しない要素にアクセスをするとエラーが発生
辞書では、存在しない要素にアクセスをするとエラーが発生します。Counterでエラーが発生しません。辞書を使って各キーの出現回数をカウントする方法はpython 辞書(ディクショナリ―)内の各キーの出現回数をカウント!を参照してください。
l = ["a", "a", "c", "b", "b"] d = dict() for i in range(len(l)): #下記の様に、Counterと同様のことを行うとエラーが発生します。 d[l[i]] += 1 #下記の様にする必要があります。出力は右記です:{'a': 2, 'c': 1, 'b': 2} # d[l[i]] = d.get(l[i], 0) + 1 print(d) """出力 KeyError: 'a' """
Counterクラスの場合は、存在しない要素にアクセスした場合にエラーが発生しません。こちらのコードの②を参照してください。
collections — コンテナデータ型 — Python 3.9.4 ドキュメントに説明があります。
要素の出現回数をカウントをするためにループが必要
辞書は要素の出現回数をカウントをするためにループが必要ですが、Counterクラスの場合は必ずしも必要ではありません。
l = ["a", "a", "c", "b", "b"] d1 = dict() for i in range(len(l)): d1[l[i]] = d1.get(l[i], 0) + 1 print(d1) """出力 {'a': 2, 'c': 1, 'b': 2} """
Counterクラスの場合は、Counter(リスト)とするだけで上記と同様のことができます。こちらのコードの①を参照してください。
コメント