在本教程中,您将学习如何使用 Python 集合模块中的计数器对象。
当您在 Python 中处理长序列时,例如 Python 列表或字符串,您有时可能需要存储出现在序列中的项目以及它们出现的次数。
Python 字典是适合此类应用程序的内置数据结构。 然而,来自 collections 模块的 Python Counter 类可以简化这一点——通过构造一个计数器——它是一个包含项目及其在序列中的计数的字典。
在接下来的几分钟内,您将了解以下内容:
- 使用 Python 的计数器对象
- 创建一个 Python 字典以将项目的计数值存储在可迭代对象中
- 使用简化语法的 Python 计数器重写字典
- 执行诸如更新和减去元素、查找两个计数器对象之间的交集等操作
- 使用 most_common() 方法获取计数器中出现频率最高的项目
让我们开始吧!
Python 集合模块和计数器类
您将经常使用 Python 字典来将项目及其计数存储在可迭代对象中。 项目和计数分别存储为键和值。
由于 Counter 类是 Python 内置集合模块的一部分,您可以像这样在 Python 脚本中导入它:
from collections import Counter
如上所述导入 Counter 类后,您可以实例化一个计数器对象,如下所示:
<counter_object> = Counter(iterable)
这里:
- iterable 是任何有效的 Python 可迭代对象,例如 Python 列表、字符串或元组。
- iterable 中的项目应该是可哈希的。
现在我们知道如何使用 Counter 从任何 Python 可迭代对象创建计数器对象,让我们开始编码。
本教程中使用的示例可以在此 GitHub 要点中找到。
如何从 Python Iterables 创建计数器对象
让我们创建一个 Python 字符串,比如说,’renaissance’ 并将其命名为 word。
>>> word = "renaissance"
我们的目标是创建一个字典,其中单词字符串中的每个字母都映射到它在字符串中出现的次数。 一种方法是使用 for 循环,如下所示:
>>> letter_count = {} >>> for letter in word: ... if letter not in letter_count: ... letter_count[letter] = 0 ... letter_count[letter] += 1 ... >>> letter_count {'r': 1, 'e': 2, 'n': 2, 'a': 2, 'i': 1, 's': 2, 'c': 1}
让我们解析上面的代码片段做了什么:
- 将 letter_count 初始化为一个空的 Python 字典。
- 循环遍历单词字符串。
- 检查 letter_count 字典中是否存在字母。
- 如果字母不存在,则将其添加值 0,然后将值递增 1。
- word中每出现一个字母,对应字母的值就加1。
- 这一直持续到我们循环遍历整个字符串。
我们自己构建了 letter_count 字典,使用 for 循环遍历字符串单词。
现在让我们使用 collections 模块中的 Counter 类。 我们只需要将单词字符串传递给 Counter() 即可获得 letter_count 而无需遍历 iterables。
>>> from collections import Counter >>> letter_count = Counter(word) >>> letter_count Counter({'e': 2, 'n': 2, 'a': 2, 's': 2, 'r': 1, 'i': 1, 'c': 1})
计数器对象也是一个 Python 字典。 我们可以使用内置的 isinstance() 函数来验证这一点:
>>> isinstance(letter_count,dict) True
正如所见,isinstance(letter_count, dict) 返回 True,表明计数器对象 letter_count 是 Python dict 类的一个实例。
修改计数器对象
到目前为止,我们已经学会了从 Python 字符串创建计数器对象。
您还可以通过使用来自另一个可迭代对象的元素更新它们或从它们中减去另一个可迭代对象来修改计数器对象。
使用来自另一个 Iterable 的元素更新计数器
让我们初始化另一个字符串another_word:
>>> another_word = "effervescence"
假设我们想用 another_word 字符串中的项目更新 letter_count 计数器对象。
我们可以在计数器对象 letter_count 上使用 update() 方法。
>>> letter_count.update(another_word) >>> letter_count Counter({'e': 7, 'n': 3, 's': 3, 'c': 3, 'r': 2, 'a': 2, 'f': 2, 'i': 1, 'v': 1})
在输出中,我们看到计数器对象已更新为还包含字母及其在 another_word 中出现的次数。
从另一个 Iterable 中减去元素
现在让我们从 letter_count 对象中减去 another_word 的值。 为此,我们可以使用 subtract() 方法。 使用
让我们从 letter_count 中减去 another_word。
>>> letter_count.subtract(another_word) >>> letter_count Counter({'e': 2, 'n': 2, 'a': 2, 's': 2, 'r': 1, 'i': 1, 'c': 1, 'f': 0, 'v': 0})
我们看到 another_word 中的字母对应的值已经被减去,但是添加的键 ‘f’ 和 ‘v’ 并没有被删除。 它们现在映射到值 0。
注意:在这里,我们将 another_word(一个 Python 字符串)传递给 subtract() 方法调用。 我们还可以传入一个 Python 计数器对象或另一个可迭代对象。
Python 中两个计数器对象的交集
有时您可能想要找到两个 Python 计数器对象之间的交集,以确定哪些键在这两个对象之间是通用的。
让我们从 another_word 字符串 ‘effervescence’ 创建一个计数器对象,比如 letter_count_2。
>>> another_word = "effervescence" >>> letter_count_2 = Counter(another_word) >>> letter_count_2 Counter({'e': 5, 'f': 2, 'c': 2, 'r': 1, 'v': 1, 's': 1, 'n': 1})
我们可以使用简单的 & 运算符来找到 letter_count 和 letter_count_2 之间的交集。
>>> letter_count & letter_count_2 Counter({'e': 2, 'r': 1, 'n': 1, 's': 1, 'c': 1})
请注意您如何获得键以及这两个词的共同出现次数。 “renaissance”和“effervescence”都包含两次出现的“e”,以及“r”、“n”、“s”和“c”各出现一次。
使用 most_common 查找最频繁的项目
Python 计数器对象的另一个常见操作是查找最常出现的项目。
要获得计数器中前 k 个最常见的项目,您可以在计数器对象上使用 most_common() 方法。 在这里,我们在 letter_count 上调用 most_common() 来查找三个最常出现的字母。
>>> letter_count.most_common(3) [('e', 2), ('n', 2), ('a', 2)]
我们看到字母“e”、“n”和“a”在单词“renaissance”中出现了两次。
如果计数器包含大量条目并且您对使用最常用的键感兴趣,这将特别有用。
结论
以下是我们在教程中学到的内容的快速回顾:
- Python 内置集合模块中的 Counter 类可用于获取任何可迭代对象中所有项的计数值的字典。 您应该确保可迭代对象中的所有项目都是可哈希的。
- 您可以使用 update() 方法将一个 Python 计数器对象的内容更新为另一个计数器对象或任何其他可迭代对象的内容,语法为:counter1.update(counter2)。 请注意,您可以使用任何可迭代对象代替 counter2。
- 如果要从更新的计数器中删除其中一个可迭代对象的内容,可以使用 subtract() 方法:counter1.subtract(counter2)。
- 要查找两个计数器对象之间的公共元素,可以使用 & 运算符。 给定两个计数器 counter1 和 counter2,counter1 和 counter2 返回这两个计数器对象的交集。
- 要获得计数器中出现频率最高的 k 个项目,可以使用 most_common() 方法。 counter.most_common(k) 给出 k 个最常见的项目和各自的计数。
接下来,学习如何使用 default dict,collections 模块中的另一个类。 您可以使用默认字典而不是常规 Python 字典来处理丢失的键。