【Python学习】Python文件及目录操作
目录
方法2:writelines() —— 写入可迭代对象(列表、元组等)
2. 创建多层目录:os.makedirs(path, exist_ok=False)
前言
在Python编程中,文件和目录操作是最基础且常用的功能之一,广泛应用于数据读取、日志记录、批量处理文件、项目目录管理等场景。本教程将从基础概念入手,逐步讲解Python中文件的打开与关闭、读写操作,以及目录的创建、删除、遍历等核心操作,结合大量可直接运行的实例,帮助初学者快速掌握相关技能,同时补充常见问题和最佳实践,满足实际开发需求。
本教程适用于Python初学者,假设读者已掌握Python基础语法(变量、循环、条件判断等)。教程中主要使用Python内置模块(os、os.path)和Python 3.4+新增的pathlib模块(更简洁、面向对象的操作方式),两种方式均会讲解,读者可根据习惯选择使用。

第一章:文件操作基础
1.1 文件操作的核心概念
文件操作本质是“与计算机存储设备(硬盘、U盘等)进行数据交互”,核心流程分为3步:打开文件 → 操作文件(读/写等) → 关闭文件。
关键注意点:
-
打开文件后必须关闭,否则会导致资源泄露(占用系统文件句柄,长期运行可能导致程序崩溃);
-
文件路径分为“绝对路径”和“相对路径”,避免因路径错误导致操作失败;
-
不同操作系统(Windows、Linux、Mac)的路径分隔符不同(Windows用
\,Linux/Mac用/),需注意兼容性。
1.2 文件路径详解(重点)
文件路径是找到目标文件的“地址”,分为两种类型,实际开发中需灵活运用:
1.2.1 绝对路径
从计算机的“根目录”开始,完整描述文件的位置,无论程序在哪个目录运行,都能准确找到文件。
示例:
-
Windows系统:
C:\Users\Admin\Desktop\test.txt(注意:Windows中路径分隔符\需转义,或用原始字符串r"C:\Users\Admin\Desktop\test.txt"); -
Linux/Mac系统:
/home/user/Desktop/test.txt。
1.2.2 相对路径
相对于“当前程序运行的目录”(即工作目录),描述文件的位置,简洁高效,适合项目内部文件操作。
常用相对路径符号:
-
.:表示当前目录(可省略,直接写文件名即当前目录下的文件); -
..:表示上一级目录; -
./文件夹名/文件名:当前目录下的某个文件夹中的文件。
示例(假设程序在C:\Users\Admin\Desktop目录运行):
-
test.txt:等价于绝对路径C:\Users\Admin\Desktop\test.txt; -
./data/test.txt:等价于C:\Users\Admin\Desktop\data\test.txt; -
../Documents/test.txt:等价于C:\Users\Admin\Documents\test.txt。
1.3 打开与关闭文件(open()函数)
Python中使用内置函数open()打开文件,返回一个“文件对象”,通过该对象进行后续的读、写操作;操作完成后,用close()方法关闭文件。
1.3.1 open()函数语法
open(file, mode='r', buffering=-1, encoding=None, errors=None, newline=None, closefd=True, opener=None)
核心参数(重点掌握前4个):
-
file:必选参数,文件路径(绝对路径或相对路径); -
mode:可选参数,文件打开模式(决定操作类型,如读、写、追加等),默认值为'r'(只读); -
encoding:可选参数,文件编码格式(如'utf-8'、'gbk'),读取中文文件时必须指定,否则易出现乱码; -
errors:可选参数,编码错误处理方式(如'ignore'忽略错误、'replace'替换错误字符)。
1.3.2 常用文件打开模式
|
模式 |
说明 |
注意事项 |
|---|---|---|
|
r |
只读模式(默认),打开已存在的文件 |
文件不存在则报错(FileNotFoundError) |
|
w |
写入模式,打开文件后清空原有内容,重新写入 |
文件不存在则自动创建;文件存在则覆盖内容 |
|
a |
追加模式,打开文件后在末尾追加内容 |
文件不存在则自动创建;不覆盖原有内容 |
|
r+ |
读写模式,可读取也可写入 |
文件不存在则报错;写入时从当前指针位置开始,可能覆盖内容 |
|
w+ |
读写模式,先清空原有内容,再进行读写 |
文件不存在则自动创建;会覆盖原有内容 |
|
a+ |
读写模式,在文件末尾追加内容,也可读取 |
文件不存在则自动创建;读取时需移动指针(否则读不到内容) |
|
rb |
二进制只读模式,用于读取图片、视频等二进制文件 |
不指定encoding参数 |
|
wb |
二进制写入模式,用于写入图片、视频等二进制文件 |
不指定encoding参数,会覆盖原有内容 |
1.3.3 关闭文件(close()方法)
文件操作完成后,必须关闭文件,释放系统资源。有两种关闭方式:
方式1:手动关闭(不推荐)
# 打开文件
file = open('test.txt', 'r', encoding='utf-8')
# 执行操作(如读取内容)
content = file.read()
# 关闭文件
file.close()
# 注意:如果操作过程中出现异常,close()可能无法执行,导致资源泄露
方式2:with语句自动关闭(推荐)
with语句会自动管理文件资源,无论操作是否成功,都会在代码块结束后自动关闭文件,避免资源泄露,是实际开发中的首选方式。
# 格式:with open(...) as 变量名:
with open('test.txt', 'r', encoding='utf-8') as file:
# 操作文件(缩进内的代码)
content = file.read()
# 代码块结束后,文件自动关闭,无需手动调用close()
第二章:文件读写操作(核心)
文件打开后,最常用的操作就是“读”和“写”,不同打开模式对应不同的读写权限,下面分文本文件和二进制文件分别讲解。
2.1 文本文件读写(最常用)
文本文件(如.txt、.py)的读写需指定encoding(通常为'utf-8'),避免中文乱码。
2.1.1 读取文件内容
通过文件对象的3种常用方法读取内容,适用于不同场景:
方法1:read() —— 读取全部内容
语法:file.read(size=-1),size为可选参数,指定读取的字节数,默认值为-1(读取全部内容)。
# 示例:读取test.txt的全部内容
with open('test.txt', 'r', encoding='utf-8') as file:
# 读取全部内容
content = file.read()
print("文件全部内容:")
print(content)
# 示例:读取前10个字符
with open('test.txt', 'r', encoding='utf-8') as file:
content = file.read(10)
print("前10个字符:")
print(content)
注意:read()读取后,文件指针会移动到文件末尾,再次调用read()会读取到空内容。
方法2:readline() —— 逐行读取
语法:file.readline(),每次读取一行内容,换行符\n会被保留;多次调用会依次读取下一行,直到文件末尾返回空字符串。
# 示例:逐行读取文件
with open('test.txt', 'r', encoding='utf-8') as file:
# 读取第一行
line1 = file.readline()
# 读取第二行
line2 = file.readline()
print("第一行:", line1.strip()) # strip()去除换行符和空格
print("第二行:", line2.strip())
方法3:readlines() —— 读取所有行,返回列表
语法:file.readlines(),读取文件所有行,返回一个列表,每一行作为列表的一个元素(换行符\n保留)。
# 示例:读取所有行,遍历输出
with open('test.txt', 'r', encoding='utf-8') as file:
lines = file.readlines()
print("所有行(列表形式):", lines)
# 遍历列表,去除换行符
print("逐行输出:")
for line in lines:
print(line.strip())
2.1.2 写入文件内容
通过文件对象的write()和writelines()方法写入内容,需注意打开模式(w/a/r+/w+/a+)的区别。
方法1:write() —— 写入字符串
语法:file.write(string),写入指定字符串,返回写入的字符数;若打开模式为'w',会清空原有内容,再写入。
# 示例1:写入内容(覆盖原有内容)
with open('test.txt', 'w', encoding='utf-8') as file:
count = file.write("Python文件操作教程\n") # 写入字符串,添加换行符
file.write("第一章:文件操作基础")
print(f"写入的字符数:{count}") # 输出:16("Python文件操作教程\n"的长度)
# 示例2:追加内容(不覆盖原有内容)
with open('test.txt', 'a', encoding='utf-8') as file:
file.write("\n第二章:文件读写操作")
方法2:writelines() —— 写入可迭代对象(列表、元组等)
语法:file.writelines(iterable),将可迭代对象中的每个元素(字符串)写入文件,不会自动添加换行符,需手动添加。
# 示例:写入列表内容
lines = ["第三章:目录操作\n", "3.1 目录创建\n", "3.2 目录删除"]
with open('test.txt', 'a', encoding='utf-8') as file:
file.writelines(lines)
2.2 二进制文件读写
二进制文件(如图片.jpg、视频.mp4、音频.mp3)的读写,需使用二进制模式(rb/wb/ab等),不指定encoding参数,读写的是字节流(bytes类型)。
# 示例1:读取图片文件,再写入新图片(复制图片)
# 读取二进制文件
with open('test.jpg', 'rb') as file:
img_data = file.read() # 读取图片字节流
# 写入二进制文件(复制)
with open('test_copy.jpg', 'wb') as file:
file.write(img_data) # 写入字节流
print("图片复制完成")
2.3 文件指针操作
文件指针是当前读写操作的位置,默认情况下:
-
以
'r'/'rb'模式打开文件,指针在文件开头; -
以
'w'/'wb'模式打开文件,指针在文件开头(同时清空内容); -
以
'a'/'ab'模式打开文件,指针在文件末尾。
可通过以下方法操作指针:
-
file.tell():返回当前指针的位置(字节数); -
file.seek(offset, whence):移动指针到指定位置。
seek()参数说明:
-
offset:偏移量,正数表示向后移动,负数表示向前移动; -
whence:基准位置,默认值为0(文件开头),1(当前位置),2(文件末尾)。
# 示例:操作文件指针
with open('test.txt', 'r+', encoding='utf-8') as file:
# 读取前5个字符,指针移动到第5个字符后
content1 = file.read(5)
print("读取内容:", content1)
print("当前指针位置:", file.tell()) # 输出5
# 移动指针到文件开头(基准0,偏移0)
file.seek(0, 0)
print("移动后指针位置:", file.tell()) # 输出0
# 移动指针到当前位置后3个字符(基准1,偏移3)
file.seek(3, 1)
print("移动后指针位置:", file.tell()) # 输出3
# 移动指针到文件末尾前5个字符(基准2,偏移-5)
file.seek(-5, 2)
content2 = file.read()
print("读取内容:", content2)
第三章:目录操作(os模块与pathlib模块)
目录操作包括创建目录、删除目录、遍历目录、判断目录是否存在等,Python提供了os、os.path(传统方式)和pathlib(面向对象方式)两种实现方式,下面分别讲解。
3.1 os模块与os.path模块(传统方式)
os模块提供了与操作系统交互的接口,os.path模块专门用于处理文件路径,两者结合可完成所有目录操作。使用前需先导入模块:
import os
import os.path
3.1.1 查看当前工作目录
语法:os.getcwd(),返回当前程序运行的目录(字符串类型)。
import os
# 查看当前工作目录
current_dir = os.getcwd()
print("当前工作目录:", current_dir)
3.1.2 切换工作目录
语法:os.chdir(path),将当前工作目录切换到指定path路径;路径不存在则报错。
import os
# 切换到桌面目录(Windows示例)
os.chdir(r"C:\Users\Admin\Desktop")
# 验证切换结果
print("切换后的工作目录:", os.getcwd())
3.1.3 创建目录
分两种场景:创建单层目录(单个文件夹)和创建多层目录(嵌套文件夹)。
1. 创建单层目录:os.mkdir(path)
import os
# 定义目录路径(当前工作目录下的test_dir文件夹)
dir_path = "test_dir"
# 判断目录是否存在,不存在则创建
if not os.path.exists(dir_path):
os.mkdir(dir_path)
print(f"目录 {dir_path} 创建成功")
else:
print(f"目录 {dir_path} 已存在")
注意:os.mkdir()只能创建单层目录,若上级目录不存在,会报错(FileNotFoundError)。
2. 创建多层目录:os.makedirs(path, exist_ok=False)
参数exist_ok:默认值为False,若目录已存在则报错;设为True,目录已存在时不报错。
import os
# 定义多层目录路径(a/b/c)
dir_path = "a/b/c"
# 创建多层目录,目录已存在时不报错
os.makedirs(dir_path, exist_ok=True)
print(f"多层目录 {dir_path} 创建成功(若已存在则忽略)")
3.1.4 删除目录
分两种场景:删除空目录和删除非空目录(含文件/子目录)。
1. 删除空目录:os.rmdir(path)
import os
dir_path = "test_dir"
# 判断目录是否存在且为空
if os.path.exists(dir_path) and os.path.isdir(dir_path):
# 先判断目录是否为空(listdir()返回目录内的文件/子目录列表)
if len(os.listdir(dir_path)) == 0:
os.rmdir(dir_path)
print(f"空目录 {dir_path} 删除成功")
else:
print(f"目录 {dir_path} 非空,无法用rmdir删除")
else:
print(f"目录 {dir_path} 不存在")
注意:os.rmdir()只能删除空目录,若目录非空,会报错(OSError)。
2. 删除非空目录:shutil.rmtree(path)
os模块无法直接删除非空目录,需使用shutil模块(Python内置)的rmtree()方法,会递归删除目录下的所有文件和子目录,谨慎使用(不可恢复)。
import os
import shutil
dir_path = "a" # 多层目录,含子目录和文件
if os.path.exists(dir_path) and os.path.isdir(dir_path):
shutil.rmtree(dir_path)
print(f"非空目录 {dir_path} 及其内容已全部删除")
else:
print(f"目录 {dir_path} 不存在")
3.1.5 遍历目录
常用两种方法:遍历目录下的一级文件/子目录,或递归遍历所有层级的文件/子目录。
1. 遍历一级目录:os.listdir(path)
返回指定目录下的所有文件和子目录的名称列表(不递归)。
import os
dir_path = "." # 当前目录
# 遍历一级目录
items = os.listdir(dir_path)
print(f"{dir_path} 目录下的一级内容:")
for item in items:
# 拼接完整路径
item_path = os.path.join(dir_path, item)
# 判断是文件还是目录
if os.path.isfile(item_path):
print(f"文件:{item}")
else:
print(f"目录:{item}")
2. 递归遍历所有层级:os.walk(path)
返回一个生成器,每次迭代返回一个元组(当前目录路径, 子目录列表, 文件列表),可递归遍历所有子目录。
import os
dir_path = "." # 当前目录
# 递归遍历所有层级
for root, dirs, files in os.walk(dir_path):
print(f"当前目录:{root}")
print(f" 子目录:{dirs}")
print(f" 文件:{files}")
print("-" * 50)
3.1.6 路径相关判断与处理
os.path模块提供了多个常用函数,用于判断路径类型、拼接路径、获取文件名等,是实际开发中必备的工具。
|
函数 |
说明 |
示例 |
|---|---|---|
|
os.path.exists(path) |
判断路径(文件/目录)是否存在,返回布尔值 |
os.path.exists("test.txt") → True/False |
|
os.path.isfile(path) |
判断路径是否为文件,返回布尔值 |
os.path.isfile("test.txt") → True |
|
os.path.isdir(path) |
判断路径是否为目录,返回布尔值 |
os.path.isdir("test_dir") → True |
|
os.path.join(path1, path2, ...) |
拼接多个路径,自动适配操作系统的分隔符 |
os.path.join("a", "b", "test.txt") → "a/b/test.txt"(Linux) |
|
os.path.basename(path) |
获取路径中的文件名(含后缀) |
os.path.basename("a/b/test.txt") → "test.txt" |
|
os.path.dirname(path) |
获取路径中的目录部分 |
os.path.dirname("a/b/test.txt") → "a/b" |
|
os.path.split(path) |
拆分路径为(目录部分,文件名),返回元组 |
os.path.split("a/b/test.txt") → ("a/b", "test.txt") |
|
os.path.getsize(path) |
获取文件大小(字节数),目录返回0 |
os.path.getsize("test.txt") → 1024(字节) |
3.2 pathlib模块(面向对象方式,推荐)
Python 3.4+ 新增的pathlib模块,采用面向对象的思想,将路径封装为“Path对象”,操作更简洁、直观,无需拼接路径字符串,推荐用于Python 3.4以上版本的开发。使用前需导入模块:
from pathlib import Path
3.2.1 创建Path对象
Path对象可通过路径字符串创建,支持绝对路径和相对路径,自动适配操作系统。
from pathlib import Path
# 创建相对路径对象(当前目录下的test.txt)
file_path = Path("test.txt")
# 创建绝对路径对象(Windows)
abs_path = Path(r"C:\Users\Admin\Desktop\test.txt")
# 创建目录路径对象
dir_path = Path("test_dir")
print("相对路径:", file_path)
print("绝对路径:", abs_path)
print("路径是否存在:", file_path.exists())
3.2.2 路径拼接(面向对象方式)
Path对象可通过/(斜杠)直接拼接路径,无需使用os.path.join(),更简洁。
from pathlib import Path
# 拼接路径:当前目录 → a → b → test.txt
file_path = Path(".") / "a" / "b" / "test.txt"
print("拼接后的路径:", file_path)
# 转换为字符串路径(必要时)
print("字符串路径:", str(file_path))
3.2.3 目录操作(Path对象方法)
Path对象的方法与os模块功能对应,但更简洁,下面列出常用操作:
from pathlib import Path
dir_path = Path("test_dir")
multi_dir_path = Path("a/b/c")
# 1. 创建目录
dir_path.mkdir(exist_ok=True) # 单层目录,已存在不报错
multi_dir_path.mkdir(exist_ok=True, parents=True) # parents=True表示创建多层目录
# 2. 删除目录
dir_path.rmdir() # 删除空目录(非空报错)
# 删除非空目录(需结合shutil模块)
import shutil
shutil.rmtree(multi_dir_path)
# 3. 查看当前工作目录
current_dir = Path.cwd()
print("当前工作目录:", current_dir)
# 4. 切换工作目录(需结合os模块,Path无直接方法)
import os
os.chdir(current_dir / "test_dir")
# 5. 遍历目录
# 遍历一级目录
for item in dir_path.iterdir():
print(item.name) # 文件名/目录名
if item.is_file():
print(f"文件:{item}")
else:
print(f"目录:{item}")
# 递归遍历所有层级(类似os.walk())
for item in dir_path.glob("**/*"): # **/*表示递归所有文件和目录
print(item)
3.2.4 文件操作(Path对象方法)
Path对象也可直接用于文件操作,与open()函数结合使用更便捷。
from pathlib import Path
file_path = Path("test.txt")
# 1. 读取文件内容
with file_path.open("r", encoding="utf-8") as file:
content = file.read()
print("文件内容:", content)
# 2. 写入文件内容
with file_path.open("a", encoding="utf-8") as file:
file.write("\n使用pathlib操作文件")
# 3. 判断文件/目录类型
print("是否为文件:", file_path.is_file())
print("是否为目录:", file_path.is_dir())
print("文件大小:", file_path.stat().st_size) # 获取文件大小(字节)
print("文件名:", file_path.name) # 含后缀
print("文件后缀:", file_path.suffix) # 仅后缀(如.txt)
print("文件目录:", file_path.parent) # 父目录
第四章:综合案例(实战练习)
结合前面所学知识,完成两个实战案例,巩固文件和目录操作的核心技能。
案例1:批量重命名文件
需求:将指定目录下的所有.txt文件,重命名为“Python_序号_原文件名.txt”(如“Python_1_test.txt”)。
from pathlib import Path
# 1. 定义目标目录
dir_path = Path("test_files") # 假设该目录下有多个.txt文件
# 2. 判断目录是否存在
if not dir_path.exists() or not dir_path.is_dir():
print(f"目录 {dir_path} 不存在或不是目录")
else:
# 3. 遍历目录下的所有.txt文件,按顺序编号
file_list = list(dir_path.glob("*.txt")) # 获取所有.txt文件
for index, file in enumerate(file_list, start=1):
# 4. 拼接新文件名
new_name = f"Python_{index}_{file.name}"
# 5. 拼接新路径
new_path = dir_path / new_name
# 6. 重命名文件(rename()方法)
file.rename(new_path)
print(f"重命名:{file.name} → {new_name}")
print("批量重命名完成!")
案例2:遍历目录并统计文件类型
需求:递归遍历指定目录,统计所有文件的类型(按后缀分类),并输出每种类型的文件数量。
from pathlib import Path
# 1. 定义目标目录
dir_path = Path(".")
# 2. 定义字典,用于存储文件类型和数量
file_count = {}
# 3. 递归遍历所有文件
for item in dir_path.glob("**/*"):
if item.is_file(): # 只统计文件,跳过目录
# 获取文件后缀(如.txt、.py),统一转为小写
suffix = item.suffix.lower()
# 若后缀为空(无后缀文件),记为"无后缀文件"
if not suffix:
suffix = "无后缀文件"
# 更新字典计数
file_count[suffix] = file_count.get(suffix, 0) + 1
# 4. 输出统计结果
print("目录文件类型统计:")
for suffix, count in file_count.items():
print(f"{suffix} 文件:{count} 个")
第五章:常见问题与最佳实践
5.1 常见问题及解决方案
-
问题1:读取中文文件出现乱码? 解决方案:打开文件时指定
encoding='utf-8',若仍乱码,尝试encoding='gbk'(Windows系统部分文件编码为gbk)。 -
问题2:路径错误导致“FileNotFoundError”? 解决方案:检查路径是否正确(绝对路径/相对路径),使用os.path.exists()或Path.exists()判断路径是否存在;Windows路径需注意转义(用原始字符串r"")。
-
问题3:删除目录时提示“OSError: [WinError 145] 目录不是空的”? 解决方案:使用shutil.rmtree()删除非空目录,谨慎使用(不可恢复)。
-
问题4:写入文件后,打开文件看不到内容? 解决方案:确认打开模式(w/a/r+等)是否正确;若使用手动关闭文件,需确保close()执行(推荐用with语句)。
5.2 最佳实践
-
始终使用with语句打开文件,避免资源泄露;
-
路径操作优先使用pathlib模块(Python 3.4+),代码更简洁、可移植;
-
操作文件/目录前,先使用exists()判断路径是否存在,避免报错;
-
批量操作文件/目录时,加入异常处理(try-except),提升程序稳定性;
-
删除文件/目录时格外谨慎,尤其是shutil.rmtree(),可先打印操作内容,确认无误后再执行。
第六章:总结
本教程详细讲解了Python文件及目录操作的核心知识点,包括:
-
文件操作:路径概念、open()函数、文件打开模式、读写方法、文件指针操作;
-
目录操作:os模块、os.path模块、pathlib模块的常用方法(创建、删除、遍历);
-
实战案例:批量重命名文件、文件类型统计,巩固所学知识;
-
常见问题与最佳实践,帮助避免踩坑,提升开发效率。
文件和目录操作是Python开发的基础技能,建议多动手练习,结合实际场景灵活运用两种操作方式(os模块和pathlib模块),逐步掌握核心技巧。后续可结合异常处理、批量处理等需求,进一步拓展相关功能。
更多推荐



所有评论(0)