はじめに
今回はPythonのcollections.Counter()
についてまとめます。
AtCoderのPython3.4.3と3.8で動作確認済みです。
collections.Counterについて
collections.Counterは標準モジュールの一つで、リストの各要素の数え上げが出来ます。また、返り値であるCounterクラスは辞書型のサブクラスということで、辞書型と同じ操作ができます。
使い方
Counter(リスト)
でリストの要素のカウント結果を得ることができます。
from collections import Counter
a = ['a', 'b', 'c', 'd', 'a', 'a', 'b']
c = Counter(a)
print(c)
Counter({'a': 3, 'b': 2, 'c': 1, 'd': 1})
要素は数値でもカウントできます。
from collections import Counter
b = [1, 5, 4, 2, 1, 5, 5]
d = Counter(b)
print(d)
Counter({5: 3, 1: 2, 4: 1, 2: 1})
辞書型としての扱い
前述したようにCounterは辞書型として扱うことができます。 (以降、print()の後には出力が書いてあります。)
from collections import Counter
a = ['a', 'b', 'c', 'd', 'a', 'a', 'b']
c = Counter(a) # Counter({'a': 3, 'b': 2, 'c': 1, 'd': 1})
print(c.keys()) # keyを取り出す
dict_keys(['a', 'b', 'c', 'd'])
print(list(c.keys())) # keyをリストに格納
['a', 'b', 'c', 'd']
print(c.values()) # valueを取り出す
dict_values([3, 2, 1, 1])
print(list(c.values())) # valueをリストに格納
[3, 2, 1, 1]
print(c.items()) # keyとvalueを取り出す
dict_items([('a', 3), ('b', 2), ('c', 1), ('d', 1)])
print(list(c.items())) # keyとvalueをリストに格納
[('a', 3), ('b', 2), ('c', 1), ('d', 1)]
keyとして要素を指定するとその値が返ってきます。
a = ['a', 'b', 'c', 'd', 'a', 'a', 'b']
c = Counter(a)
print(c['a']) # 3
print(c['b']) # 2
zip関数を用いてkeyとvalueをまとめて受け取ることもできます。
なお、リストやタプルには*
を、辞書には**
を付けて引数に指定することにより、それらが展開されてそれぞれの要素が個別の引数として渡されます。
a = ['a', 'b', 'c', 'd', 'a', 'a', 'b']
c = Counter(a) # Counter({'a': 3, 'b': 2, 'c': 1, 'd': 1})
keys, values = zip(*c.most_common())
print(keys) # ('a', 'b', 'c', 'd')
print(values) # (3, 2, 1, 1)
Counter.most_common()
Counter
にはmost_common()
というメソッドがあります。これは(要素, 出現回数)
というタプルを出現回数順に並べたリストを返します。
from collections import Counter
a = ['a', 'b', 'c', 'd', 'a', 'a', 'b']
c = Counter(a)
d = c.most_common()
print(d) # 出現回数順のタプルのリスト
[('a', 3), ('b', 2), ('c', 1), ('d', 1)]
print(d[0]) # 1番出現回数が多いもののkeyとvalue
('a', 3)
print(d[-1]) # 1番出現回数が少ないもののkeyとvalue
('d', 1)
print(d[0][0]) # 1番出現回数が多いkey
a
print(d[0][1]) # 1番出現回数が多いkeyのvalue
3
most_common()
やcount()
をひと工夫して条件に合う要素を挙げることもできます。
from collections import Counter
a = ['a', 'b', 'c', 'd', 'a', 'a', 'b']
c = Counter(a) # Counter({'a': 3, 'b': 2, 'c': 1, 'd': 1})
d = c.most_common() # [('a', 3), ('b', 2), ('c', 1), ('d', 1)]
# 出現回数が2回以上のものを列挙(重複あり)
print([i for i in a if a.count(i) >= 2])
['a', 'b', 'a', 'a', 'b']
# 出現回数が2回以上のものを列挙(重複なし)
print([i[0] for i in c.items() if i[1] >= 2])
['a', 'b']
おわりに
読んでいただきありがとうございました。指摘等ありましたら是非コメントをお願いします。