Skip to main content

collections

1. collections 模块是什么?

collections 是 Python 内置的容器扩展包,提供了比 dictlistsettuple 更贴合特定场景的数据结构,比如计数器、队列、命名元组等。它无需额外安装,是写脚本、处理数据时提升效率的“标准工具箱”。

2. 如何开始使用?

collections 随 Python 一起发布,因此 Windows 与 macOS 不需要任何安装命令 。只需 import collections(或直接导入需要的类型)即可。下面的脚本展示了如何检查模块版本并验证可用性:

# 说明:导入 collections 模块以检查可用性
import collections

if __name__ == "__main__":
# 说明:输出模块所在的物理路径
print(f"collections 模块所在路径:{collections.__file__}")
# 说明:展示模块内的一个示例类型
print(f"默认字典类型:{collections.defaultdict}")

3. 核心数据类型一览

本章分别介绍最常用的六种容器,并配套可独立运行的 Python 脚本,帮助你立即上手。

3.1 Counter:统计出现次数

Counter 适合统计列表、字符串或其他可哈希对象的频率。

# 说明:导入 Counter 用于统计元素出现次数
from collections import Counter

def main() -> None:
# 说明:准备一个包含重复单词的列表
words = ["apple", "banana", "apple", "orange", "banana", "apple"]
# 说明:统计列表中每个单词出现次数
word_counter = Counter(words)
print("词频:", word_counter)

# 说明:直接对字符串执行统计
char_counter = Counter("programming")
print("字符频率:", char_counter)

# 说明:获取出现次数最多的两个单词
print("出现次数最多的 2 个词:", word_counter.most_common(2))

# 说明:演示 Counter 之间的加法合并
merged = Counter(["a", "b", "c"]) + Counter(["b", "c", "d"])
print("合并后的计数器:", merged)

if __name__ == "__main__":
main()

3.2 defaultdict:带默认值的字典

defaultdict 可以为缺失的 key 自动创建默认值,避免 KeyError。

# 说明:导入 defaultdict 以设置自动默认值
from collections import defaultdict

def main() -> None:
# 说明:创建以 list 为默认值的字典
list_dict = defaultdict(list)
list_dict["fruits"].append("apple")
list_dict["fruits"].append("banana")
print("列表默认值示例:", list_dict)

# 说明:创建以 int 为默认值的计数字典
count_dict = defaultdict(int)
for word in ["apple", "banana", "apple", "orange"]:
count_dict[word] += 1
print("整数默认值示例:", count_dict)

# 说明:定义自定义默认值函数
def fallback() -> str:
return "未知"

# 说明:使用自定义函数作为默认值
custom_dict = defaultdict(fallback)
print("自定义默认值:", custom_dict["name"])

if __name__ == "__main__":
main()

3.3 deque:双端队列

deque 具备 O(1) 的两端插入/删除性能,适合实现队列、栈或滑动窗口。

# 说明:导入 deque 用于构建双端队列
from collections import deque

def main() -> None:
# 说明:初始化队列并从右端、左端分别添加
dq = deque(["b", "c", "d"])
dq.append("e")
dq.appendleft("a")
print("添加元素后:", dq)

# 说明:分别从右侧和左侧弹出元素
right = dq.pop()
left = dq.popleft()
print("弹出元素:", left, right)
print("当前队列:", dq)

# 说明:扩展队列并旋转以模拟窗口移动
dq.extend(["e", "f"])
dq.extendleft(["z"])
dq.rotate(2)
print("扩展并旋转后的队列:", dq)

if __name__ == "__main__":
main()

3.4 namedtuple:带字段名的元组

namedtuple 提供“字段名 + 元组”的双重便利,适用于轻量数据结构。

# 说明:导入 namedtuple 用于创建带字段名的元组
from collections import namedtuple

def main() -> None:
# 说明:定义两个命名元组类型
Point = namedtuple("Point", ["x", "y"])
Person = namedtuple("Person", "name age city")

# 说明:创建命名元组实例
p1 = Point(10, 20)
person = Person("Alice", 25, "Beijing")

# 说明:通过字段名访问各属性
print("坐标:", p1.x, p1.y)
print("人物信息:", person.name, person.age, person.city)
print("转换为字典:", person._asdict())

if __name__ == "__main__":
main()

3.5 OrderedDict:有序字典

在需要精确控制插入顺序或移动元素时,OrderedDict 仍然有用。

# 说明:导入 OrderedDict 以保持插入顺序
from collections import OrderedDict

def main() -> None:
# 说明:按特定顺序插入键值
od = OrderedDict()
od["z"] = 1
od["a"] = 2
od["c"] = 3
print("初始顺序:", od)

# 说明:把指定键移动到末尾
od.move_to_end("z")
print("移动 z 到末尾:", od)

# 说明:弹出键 a 以及最后一个键
od.pop("a")
last_key, last_value = od.popitem()
print("弹出元素后:", od, "| 最后弹出:", (last_key, last_value))

if __name__ == "__main__":
main()

3.6 ChainMap:链接多个字典

ChainMap 提供“多层字典合并视图”,常用于配置合并、作用域查找。

# 说明:导入 ChainMap 用于合并多层配置
from collections import ChainMap

def main() -> None:
# 说明:依次准备默认、环境、用户配置
defaults = {"theme": "light", "lang": "zh"}
env = {"lang": "en"}
user = {"theme": "dark"}

# 说明:创建链式映射以统一读取
settings = ChainMap(user, env, defaults)
print("当前配置:", dict(settings))
# 说明:更新配置将作用于第一个映射
settings["lang"] = "jp"
print("更新后的配置:", dict(settings))

if __name__ == "__main__":
main()

4. 实战案例

掌握基本类型后,可以把它们用于更贴近工作/学习的场景。

4.1 文本词频统计

# 说明:导入 Counter 和正则工具统计词频
from collections import Counter
import re

def main() -> None:
# 说明:将文本转换为小写并切分为单词
text = "hello world hello python world python python"
words = re.findall(r"\w+", text.lower())
# 说明:统计每个单词出现次数
freq = Counter(words)
print("最高频词:", freq.most_common(3))

if __name__ == "__main__":
main()

4.2 构建树状数据

# 说明:导入 defaultdict 构建无限深度的树结构
from collections import defaultdict

def tree():
# 说明:返回自身类型作为默认值,实现自动嵌套
return defaultdict(tree)

def main() -> None:
# 说明:创建模拟文件系统并写入示例数据
file_system = tree()
file_system["home"]["user"]["documents"]["file.txt"] = "content"
file_system["home"]["user"]["downloads"]["app.zip"] = "data"
print("读取文件内容:", file_system["home"]["user"]["documents"]["file.txt"])

if __name__ == "__main__":
main()

4.3 最近最少使用缓存(LRU)

# 说明:基于 OrderedDict 实现简单 LRU 缓存
from collections import OrderedDict

class LRUCache:
def __init__(self, capacity: int):
# 说明:使用 OrderedDict 保存缓存项
self.cache = OrderedDict()
self.capacity = capacity

def get(self, key):
# 说明:命中后将元素移动到队尾表示最近使用
if key not in self.cache:
return -1
self.cache.move_to_end(key)
return self.cache[key]

def put(self, key, value):
# 说明:更新或添加键,并移动到队尾
if key in self.cache:
self.cache.move_to_end(key)
self.cache[key] = value
# 说明:超出容量时弹出最旧的数据
if len(self.cache) > self.capacity:
self.cache.popitem(last=False)

def main() -> None:
# 说明:创建容量为 2 的缓存并测试行为
cache = LRUCache(2)
cache.put(1, "A")
cache.put(2, "B")
print(cache.get(1))
cache.put(3, "C")
print(cache.get(2))

if __name__ == "__main__":
main()

5. 总结与对比

数据类型主要用途上手难度适用场景
Counter统计元素频率词频、库存统计
defaultdict缺省值字典数据归类、计数
deque双端队列★★队列/栈、滑动窗口
namedtuple轻量数据结构★★坐标、记录对象
OrderedDict有序字典★★LRU 缓存、顺序控制
ChainMap多配置合并★★配置覆盖、作用域