文章目录

Python提供了多种模块进行目录操作,主要包括os/os.path、pathlib和shutil。os模块提供传统方法如mkdir/listdir等,pathlib(Python3.4+推荐)采用面向对象方式操作路径,而shutil支持高级目录操作。核心功能包括:创建/删除目录(mkdir/rmdir)、路径拼接(join/Path对象)、遍历目录(walk/iterdir)、文件搜索(glob/rglob)以及获取目录信息(stat)。pathlib通过Path对象提供更直观的操作方式,如使用/拼接路径、属性访问等
Python 目录操作详解
目录操作是文件系统管理的重要组成部分,Python 提供了多种方式来处理目录。下面我将从基础到高级,全面详细地讲解 Python 中的目录操作。
一、目录操作基础模块
Python 主要使用以下模块进行目录操作:
- os 模块:传统的目录操作方法
- os.path 模块:路径相关操作
- pathlib 模块(Python 3.4+):面向对象的路径操作(推荐)
- shutil 模块:高级文件和目录操作
[目录操作模块]
├── os/os.path (传统方法)
├── pathlib (现代面向对象方法)
└── shutil (高级操作)
二、使用 os 和 os.path 进行目录操作
1. 基本目录操作
操作 | 方法 | 描述 |
---|---|---|
创建目录 | os.mkdir(path) |
创建单个目录 |
递归创建 | os.makedirs(path) |
创建多级目录 |
删除目录 | os.rmdir(path) |
删除空目录 |
递归删除 | shutil.rmtree(path) |
删除目录及其内容 |
列出目录 | os.listdir(path) |
返回目录内容列表 |
当前目录 | os.getcwd() |
获取当前工作目录 |
改变目录 | os.chdir(path) |
改变当前工作目录 |
2. 路径操作(os.path)
操作 | 方法 | 描述 |
---|---|---|
路径拼接 | os.path.join(a, b) |
拼接路径 |
绝对路径 | os.path.abspath(path) |
获取绝对路径 |
路径存在 | os.path.exists(path) |
检查路径是否存在 |
是文件 | os.path.isfile(path) |
检查是否是文件 |
是目录 | os.path.isdir(path) |
检查是否是目录 |
路径分割 | os.path.split(path) |
分割为(目录, 文件名) |
扩展名 | os.path.splitext(path) |
分割为(路径, 扩展名) |
3. 代码示例
import os
import shutil
# 创建目录
if not os.path.exists('new_dir'):
os.mkdir('new_dir') # 创建单个目录
os.makedirs('path/to/nested/dir') # 创建多级目录
# 列出目录内容
print(os.listdir('.')) # 当前目录内容
# 删除目录
os.rmdir('new_dir') # 只能删除空目录
shutil.rmtree('path') # 删除整个目录树
# 路径操作示例
path = os.path.join('dir', 'subdir', 'file.txt') # dir/subdir/file.txt
print(os.path.abspath('.')) # 当前目录的绝对路径
print(os.path.isdir('/path/to/dir')) # 检查是否是目录
三、使用 pathlib 进行目录操作(推荐)
pathlib
是 Python 3.4+ 引入的面向对象的路径操作模块,更加直观和安全。
1. Path 对象基本操作
操作 | 方法/属性 | 描述 |
---|---|---|
创建对象 | Path(path) |
创建Path对象 |
路径拼接 | / 运算符 |
路径拼接 |
获取父目录 | .parent |
父目录Path对象 |
获取文件名 | .name |
文件名部分 |
获取后缀 | .suffix |
文件扩展名 |
无后缀名 | .stem |
不带扩展名的文件名 |
判断存在 | .exists() |
路径是否存在 |
是文件 | .is_file() |
是否是文件 |
是目录 | .is_dir() |
是否是目录 |
2. 目录操作
操作 | 方法 | 描述 |
---|---|---|
创建目录 | .mkdir() |
创建目录 |
删除目录 | .rmdir() |
删除空目录 |
遍历目录 | .iterdir() |
生成目录内容 |
通配查找 | .glob() |
模式匹配文件 |
递归查找 | .rglob() |
递归模式匹配 |
3. 代码示例
from pathlib import Path
# 创建Path对象
p = Path('/home/user/documents') / 'report.txt' # 使用/拼接路径
print(p) # /home/user/documents/report.txt
# 路径属性
print(p.parent) # /home/user/documents
print(p.name) # report.txt
print(p.stem) # report
print(p.suffix) # .txt
# 目录操作
new_dir = Path('new_directory')
new_dir.mkdir(exist_ok=True) # 创建目录,exist_ok=True避免已存在时报错
# 遍历目录
for item in Path('.').iterdir(): # 当前目录内容
print(item.name)
# 模式匹配
for py_file in Path('.').glob('*.py'): # 所有.py文件
print(py_file)
# 递归查找
for txt_file in Path('.').rglob('*.txt'): # 所有子目录中的.txt文件
print(txt_file)
四、目录遍历与搜索
1. 递归遍历目录树
import os
# 使用os.walk递归遍历
for root, dirs, files in os.walk('.'):
print(f"当前目录: {root}")
print(f"子目录: {dirs}")
print(f"文件: {files}")
print("-" * 40)
# 使用pathlib的rglob
from pathlib import Path
for path in Path('.').rglob('*'):
print(path)
2. 查找特定文件
from pathlib import Path
# 查找所有Python文件
py_files = list(Path('.').glob('**/*.py')) # 方法1
py_files = list(Path('.').rglob('*.py')) # 方法2
# 查找最近修改的文件
from datetime import datetime, timedelta
def find_recent_files(directory, days=7):
cutoff = datetime.now() - timedelta(days=days)
for item in Path(directory).rglob('*'):
if item.is_file() and datetime.fromtimestamp(item.stat().st_mtime) > cutoff:
yield item
for recent_file in find_recent_files('.'):
print(recent_file)
五、目录与文件信息
1. 获取详细信息
from pathlib import Path
import time
p = Path('example.txt')
# 获取文件/目录信息
stat = p.stat()
print(f"大小: {stat.st_size} 字节") # 文件大小
print(f"修改时间: {time.ctime(stat.st_mtime)}") # 最后修改时间
print(f"创建时间: {time.ctime(stat.st_ctime)}") # 创建时间(Windows)
print(f"访问时间: {time.ctime(stat.st_atime)}") # 最后访问时间
# 获取目录占用空间
def get_dir_size(path):
return sum(f.stat().st_size for f in Path(path).rglob('*') if f.is_file())
print(f"目录大小: {get_dir_size('.')} 字节")
2. 权限与属性
import os
from pathlib import Path
# 检查权限
print(os.access('file.txt', os.R_OK)) # 可读
print(os.access('file.txt', os.W_OK)) # 可写
print(os.access('file.txt', os.X_OK)) # 可执行
# 修改权限 (Unix-like系统)
Path('script.sh').chmod(0o755) # rwxr-xr-x
# 修改所有者 (Unix-like系统)
import pwd, grp
uid = pwd.getpwnam('username').pw_uid
gid = grp.getgrnam('groupname').gr_gid
os.chown('file.txt', uid, gid)
六、高级目录操作
1. 目录比较与同步
from filecmp import dircmp
# 比较两个目录
cmp = dircmp('dir1', 'dir2')
cmp.report() # 打印比较结果
# 获取差异详情
print("相同文件:", cmp.same_files)
print("dir1独有:", cmp.left_only)
print("dir2独有:", cmp.right_only)
print("差异文件:", cmp.diff_files)
2. 临时目录
import tempfile
# 创建临时目录
with tempfile.TemporaryDirectory() as tmpdir:
print(f"临时目录: {tmpdir}")
# 在此使用临时目录
(Path(tmpdir) / 'tempfile.txt').write_text("临时内容")
# 退出with后自动删除
# 不自动删除的临时目录
tmpdir = tempfile.mkdtemp()
print(f"临时目录: {tmpdir}")
# 使用完后需要手动删除
import shutil
shutil.rmtree(tmpdir)
七、跨平台注意事项
路径分隔符:
- Windows 使用
\
- Linux/macOS 使用
/
- 推荐:总是使用
/
,Python会自动转换,或使用os.path.join()
/pathlib
- Windows 使用
路径大小写:
- Windows 路径不区分大小写
- Linux/macOS 区分大小写
符号链接:
- 使用
os.path.islink()
或Path.is_symlink()
检查 os.readlink()
或Path.readlink()
获取链接目标
- 使用
隐藏文件:
- Unix-like 系统以
.
开头的文件是隐藏文件 - Windows 有隐藏属性
- Unix-like 系统以
# 跨平台路径处理最佳实践
from pathlib import Path
# 创建跨平台安全路径
config_path = Path.home() / 'app' / 'config.ini' # 用户主目录下的app/config.ini
# 处理隐藏文件
def list_all_files(path):
return [p for p in Path(path).rglob('*') if not p.name.startswith('.')]
八、最佳实践总结
- 优先使用 pathlib:比 os.path 更现代、更安全
- 处理异常:检查目录是否存在或捕获异常
- 递归操作谨慎:特别是删除操作,确保不会误删
- 路径安全:避免路径遍历漏洞,不要直接使用用户输入拼接路径
- 资源管理:使用 with 语句管理临时目录
from pathlib import Path
import shutil
def safe_copy(src, dst):
"""安全复制文件,防止路径遍历攻击"""
src_path = Path(src).resolve() # 解析为绝对路径
dst_path = Path(dst).resolve()
# 检查src是否在允许的目录内
allowed_dir = Path('/allowed/directory').resolve()
if not src_path.is_relative_to(allowed_dir):
raise ValueError("源路径不在允许的目录内")
# 确保目标目录存在
dst_path.parent.mkdir(parents=True, exist_ok=True)
# 执行复制
shutil.copy(src_path, dst_path)
通过以上详细讲解,你应该对 Python 中的目录操作有了全面的了解。掌握这些知识将帮助你高效地处理文件系统中的各种任务!