本文介绍如何通过纯 python 循环(不依赖正则表达式)从文件名列表中提取扩展名,并统计每种扩展名的出现频次,最终以字典形式返回(键为扩展名,值为出现次数)。
本文介绍如何通过纯 python 循环(不依赖正则表达式)从文件名列表中提取扩展名,并统计每种扩展名的出现频次,最终以字典形式返回(键为扩展名,值为出现次数)。
要实现 count_file_types(["image1.jpg", "image2.jpg", "preso.pptx"]) → {"jpg": 2, "pptx": 1},核心在于两步:提取扩展名 和 统计频次。注意:扩展名指文件名中最后一个点(.)之后的部分(如 "image1.jpg" 的扩展名是 "jpg"),且需忽略大小写差异(通常建议统一转小写以提升鲁棒性)。
✅ 正确的循环实现(无正则、无第三方库)
def count_file_types(file_list):
ext_count = {}
for filename in file_list:
# 安全提取扩展名:仅取最后一个点后的部分,若无点则为空字符串
if '.' in filename:
ext = filename.split('.')[-1]
# 可选:转小写,避免 "JPG" 和 "jpg" 被视为不同扩展名
ext = ext.lower()
else:
ext = "" # 或跳过无扩展名文件,依需求而定
# 统计频次
if ext in ext_count:
ext_count[ext] += 1
else:
ext_count[ext] = 1
return ext_count调用示例:
print(count_file_types(["image1.jpg", "image2.jpg", "preso.pptx"]))
# 输出: {'jpg': 2, 'pptx': 1}
print(count_file_types(["doc.TXT", "readme.md", "archive.tar.gz"]))
# 输出: {'txt': 1, 'md': 1, 'gz': 1} ← 注意:此逻辑取最后一个点后内容,故 "tar.gz" 的扩展名是 "gz"⚠️ 注意事项:
- filename.split('.')[-1] 是简洁安全的提取方式,比 filename.rsplit('.', 1)[-1] 更直观,但二者在多数场景效果一致;
- 若需支持多级扩展名(如 "archive.tar.gz" 视为 "tar.gz"),应改用 rsplit('.', 1) 并判断分割结果长度;
- 原问题代码错误在于:arr.append(i.split(".")) 生成的是二维列表(如 [["image1","jpg"], ...]),后续却直接对子列表 i 做字典键判断(列表不可哈希);且 freq[item] = 1 中变量名 item 未定义,属语法错误;
- print() 放在 return 之后永远不会执行——Python 函数遇到 return 即终止。
✅ 进阶推荐:使用标准库提升可读性与健壮性
虽然题目要求“不用正则”,但推荐使用 pathlib.Path(Python 3.4+ 内置)处理路径更规范:
from pathlib import Path
def count_file_types(file_list):
ext_count = {}
for f in file_list:
ext = Path(f).suffix.lstrip('.') # 自动处理路径,.suffix 包含点,故需 lstrip
if ext: # 忽略无扩展名文件
ext = ext.lower()
ext_count[ext] = ext_count.get(ext, 0) + 1
return ext_count或进一步简化为一行式(仍基于循环思想,get() 是内置安全计数模式):
def count_file_types(file_list):
ext_count = {}
for f in file_list:
ext = Path(f).suffix.lstrip('.').lower()
if ext:
ext_count[ext] = ext_count.get(ext, 0) + 1
return ext_count✅ 总结:掌握 str.split('.')[-1] 提取扩展名 + 字典手动计数(if key in dict 或 dict.get())是基础关键;引入 pathlib 可提升路径处理可靠性;始终注意边界情况(空扩展名、大小写、隐藏文件等),即可写出健壮、可维护的文件类型统计函数。

















