
本文介绍使用defaultdict嵌套counter结构,高效统计分词标注文本中每个单词的总出现次数及其对应各词性(pos)标签的频次分布,并输出结构化结果。
本文介绍使用defaultdict嵌套counter结构,高效统计分词标注文本中每个单词的总出现次数及其对应各词性(pos)标签的频次分布,并输出结构化结果。
在自然语言处理的预处理阶段,常需解析形如 word/POS 的标注文本(如Penn Treebank格式),并统计每个单词的全局频次及它在不同词性标签下的分布情况。例如,动词“reported”可能同时标注为过去分词 VBN(7次)和过去式 VBD(9次),需合并呈现。
最简洁高效的方案是采用 collections.defaultdict(Counter):外层 defaultdict 自动为每个新单词初始化一个 Counter 对象,内层 Counter 则专门负责该单词下各POS标签的计数。相比手动检查键存在性或嵌套字典,此结构既避免 KeyError,又天然支持累加与聚合操作。
以下是完整可运行示例:
SkillSub Pro - Python 题解与代码注释双功能技能功能概述SkillSub Pro - Python 题解与代码注释双功能技能是一项面向实际任务的技能,主要用于SkillSub Pro 是一个 Python 题解生成与代码注释的 双功能合体技能 ,专为学生、算法学习者和开发者设计;✅ 一个技能,两种用途 :;核心要点📝 题解模式 :输入题目/题号,自动生成完整 Python 题解(含详细注释、解题思路、复杂度分析);💬 注释模式 :输入 Python 代码,自动添加详细中。它将相关步骤、
from collections import defaultdict, Counter
input_filename = "pos_tagged.txt"
wordcounts = defaultdict(Counter)
with open(input_filename, "r") as f:
for line in f:
line = line.strip()
if not line: # 跳过空行
continue
try:
word, pos = line.rsplit('/', 1) # 仅从右侧分割一次,兼容含斜杠的词(如 "U.S./NNP")
wordcounts[word][pos] += 1
except ValueError:
continue # 忽略格式异常行(如无 '/' 的脏数据)
# 输出:单词、总频次、POS标签及对应频次(按出现顺序排列)
for word, pos_counter in wordcounts.items():
total = pos_counter.total() # Python 3.10+;旧版本可用 sum(pos_counter.values())
pos_parts = [f"{pos} {count}" for pos, count in pos_counter.items()]
print(f"{word}\t{total}\t{' '.join(pos_parts)}")关键注意事项:
立即学习“Python免费学习笔记(深入)”;
- 使用
line.strip()预处理每行,消除换行符与首尾空格,防止rsplit失败; -
rsplit('/', 1)确保只分割最右侧的/,避免误切含斜杠的单词(如"U.S./NNP"); -
Counter.total()在 Python ≥3.10 可用;若使用旧版本,请替换为sum(pos_counter.values()); - 输出字段间建议用制表符
\t分隔,便于后续导入Excel或pandas;如需固定列宽对齐,可用str.ljust()或format()控制; - 若需按总频次降序排列,可在循环前添加:
for word, pos_counter in sorted(wordcounts.items(), key=lambda x: -x[1].total()):。
该方法时间复杂度为 O(n),空间利用率高,代码简洁且具备良好可扩展性——如后续需增加词形归一化(lemma)或上下文特征,只需在 word 键生成逻辑处扩展即可。

















