Python的IO(输入/输出)操作是编程中非常基础且重要的部分,它允许程序与外部世界进行交互。本文将详细介绍Python中的文件读写操作、标准输入输出以及相关的最佳实践。

一、文件读写操作

1. 打开和关闭文件

在Python中,使用open()函数打开文件,使用close()方法关闭文件。

1
2
3
4
5
6
7
8
9
# 打开文件
file = open('example.txt', 'r')

# 操作文件
content = file.read()
print(content)

# 关闭文件
file.close()

2. 文件打开模式

模式 描述
r 只读模式(默认)
w 写入模式,会覆盖现有文件
a 追加模式,在文件末尾添加内容
x 独占创建模式,如果文件已存在则报错
b 二进制模式
t 文本模式(默认)
+ 读写模式
1
2
3
4
5
6
7
8
# 二进制模式打开
with open('image.jpg', 'rb') as f:
data = f.read()

# 读写模式打开
with open('example.txt', 'r+') as f:
content = f.read()
f.write('Additional content')

3. 使用with语句

with语句是处理文件的推荐方式,它会自动管理文件的关闭,即使出现异常也能保证文件正确关闭。

1
2
3
4
5
# 使用with语句
with open('example.txt', 'r') as file:
content = file.read()
print(content)
# 文件自动关闭

4. 读取文件内容

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
# 读取整个文件
with open('example.txt', 'r') as f:
content = f.read()
print(content)

# 逐行读取
with open('example.txt', 'r') as f:
for line in f:
print(line.strip())

# 读取指定数量的字符
with open('example.txt', 'r') as f:
content = f.read(100) # 读取前100个字符
print(content)

# 读取所有行到列表
with open('example.txt', 'r') as f:
lines = f.readlines()
print(lines)

5. 写入文件内容

1
2
3
4
5
6
7
8
9
10
11
12
13
# 写入文件(覆盖)
with open('example.txt', 'w') as f:
f.write('Hello, world!\n')
f.write('This is a test.\n')

# 追加内容
with open('example.txt', 'a') as f:
f.write('Additional line.\n')

# 写入多行
lines = ['Line 1\n', 'Line 2\n', 'Line 3\n']
with open('example.txt', 'w') as f:
f.writelines(lines)

二、标准输入输出

1. 标准输出(print)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
# 基本输出
print('Hello, world!')

# 多个参数
print('Hello', 'world', '!')

# 自定义分隔符
print('Hello', 'world', sep=', ')

# 自定义结束符
print('Hello', end=' ')
print('world')

# 格式化输出
name = 'Alice'
age = 25
print(f'Name: {name}, Age: {age}')
print('Name: {}, Age: {}'.format(name, age))
print('Name: %s, Age: %d' % (name, age))

2. 标准输入(input)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
# 基本输入
name = input('Enter your name: ')
print(f'Hello, {name}!')

# 输入转换
age = int(input('Enter your age: '))
print(f'You are {age} years old.')

# 多行输入
print('Enter multiple lines (press Ctrl+D to end):')
lines = []
while True:
try:
line = input()
lines.append(line)
except EOFError:
break
print('You entered:')
for line in lines:
print(line)

三、二进制文件操作

1. 读取二进制文件

1
2
3
4
5
6
7
8
9
# 读取图片文件
with open('image.jpg', 'rb') as f:
data = f.read()
print(f'File size: {len(data)} bytes')

# 读取部分二进制数据
with open('image.jpg', 'rb') as f:
header = f.read(10) # 读取文件头
print(f'Header: {header}')

2. 写入二进制文件

1
2
3
4
5
6
7
8
9
10
11
12
13
# 写入二进制数据
data = b'Hello, binary world!'
with open('binary.bin', 'wb') as f:
f.write(data)

# 复制二进制文件
with open('source.jpg', 'rb') as src:
with open('destination.jpg', 'wb') as dst:
while True:
chunk = src.read(1024) # 每次读取1024字节
if not chunk:
break
dst.write(chunk)

四、文件位置操作

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
# 文件位置操作
with open('example.txt', 'r+') as f:
# 获取当前位置
print(f'Current position: {f.tell()}')

# 读取部分内容
content = f.read(10)
print(f'Read: {content}')
print(f'Position after read: {f.tell()}')

# 移动到文件开头
f.seek(0)
print(f'Position after seek(0): {f.tell()}')

# 移动到文件末尾
f.seek(0, 2) # 0表示偏移量,2表示相对于文件末尾
print(f'Position at end: {f.tell()}')

五、异常处理

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
# 文件操作的异常处理
try:
with open('non_existent_file.txt', 'r') as f:
content = f.read()
except FileNotFoundError:
print('Error: File not found')
except PermissionError:
print('Error: Permission denied')
except Exception as e:
print(f'Error: {e}')

# 写入文件的异常处理
try:
with open('protected_file.txt', 'w') as f:
f.write('Test content')
except Exception as e:
print(f'Error writing file: {e}')

六、高级文件操作

1. 文件路径操作

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
import os
import pathlib

# 获取当前目录
print(f'Current directory: {os.getcwd()}')

# 拼接路径
file_path = os.path.join('data', 'example.txt')
print(f'File path: {file_path}')

# 检查文件是否存在
print(f'File exists: {os.path.exists(file_path)}')

# 使用pathlib(推荐)
path = pathlib.Path('data') / 'example.txt'
print(f'Path: {path}')
print(f'Path exists: {path.exists()}')

2. 文件信息

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
import os
import stat

# 获取文件信息
file_path = 'example.txt'
if os.path.exists(file_path):
print(f'File size: {os.path.getsize(file_path)} bytes')
print(f'Last modified: {os.path.getmtime(file_path)}')
print(f'Is file: {os.path.isfile(file_path)}')
print(f'Is directory: {os.path.isdir(file_path)}')

# 使用pathlib
from pathlib import Path
path = Path('example.txt')
if path.exists():
print(f'File size: {path.stat().st_size} bytes')
print(f'Last modified: {path.stat().st_mtime}')
print(f'Is file: {path.is_file()}')
print(f'Is directory: {path.is_dir()}')

七、综合示例

1. 文本文件处理

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
文本文件处理示例
"""

def read_file(file_path):
"""读取文件内容"""
try:
with open(file_path, 'r', encoding='utf-8') as f:
return f.read()
except Exception as e:
print(f'Error reading file: {e}')
return None

def write_file(file_path, content):
"""写入文件内容"""
try:
with open(file_path, 'w', encoding='utf-8') as f:
f.write(content)
return True
except Exception as e:
print(f'Error writing file: {e}')
return False

def append_file(file_path, content):
"""追加文件内容"""
try:
with open(file_path, 'a', encoding='utf-8') as f:
f.write(content)
return True
except Exception as e:
print(f'Error appending file: {e}')
return False

def count_lines(file_path):
"""统计文件行数"""
try:
with open(file_path, 'r', encoding='utf-8') as f:
return sum(1 for line in f)
except Exception as e:
print(f'Error counting lines: {e}')
return 0

def main():
# 测试文件操作
test_file = 'test.txt'

# 写入测试内容
content = 'Hello, world!\nThis is a test.\nPython IO operations.'
if write_file(test_file, content):
print(f'File {test_file} created successfully.')

# 读取文件内容
file_content = read_file(test_file)
if file_content:
print(f'File content:\n{file_content}')

# 追加内容
append_content = '\nAdditional line.'
if append_file(test_file, append_content):
print('Content appended successfully.')

# 再次读取
file_content = read_file(test_file)
if file_content:
print(f'Updated file content:\n{file_content}')

# 统计行数
line_count = count_lines(test_file)
print(f'Number of lines: {line_count}')

if __name__ == '__main__':
main()

2. 二进制文件处理

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
二进制文件处理示例
"""

def copy_file(src_path, dst_path):
"""复制文件"""
try:
with open(src_path, 'rb') as src:
with open(dst_path, 'wb') as dst:
# 分块读取写入,适用于大文件
while True:
chunk = src.read(1024 * 1024) # 1MB chunks
if not chunk:
break
dst.write(chunk)
print(f'File copied from {src_path} to {dst_path}')
return True
except Exception as e:
print(f'Error copying file: {e}')
return False

def read_binary_file(file_path):
"""读取二进制文件"""
try:
with open(file_path, 'rb') as f:
return f.read()
except Exception as e:
print(f'Error reading binary file: {e}')
return None

def main():
# 测试二进制文件操作
test_file = 'test.bin'

# 写入二进制数据
binary_data = b'Hello, binary world!\x00\x01\x02\x03'
with open(test_file, 'wb') as f:
f.write(binary_data)
print(f'Binary file {test_file} created.')

# 读取二进制数据
data = read_binary_file(test_file)
if data:
print(f'Read {len(data)} bytes: {data}')

# 复制文件
copy_file(test_file, 'test_copy.bin')

if __name__ == '__main__':
main()

八、最佳实践

  1. 始终使用with语句:确保文件正确关闭,避免资源泄漏
  2. 指定编码:在处理文本文件时,明确指定编码(如utf-8)
  3. 异常处理:捕获并处理可能的文件操作异常
  4. 分块处理:对于大文件,使用分块读取和写入
  5. 使用pathlib:对于路径操作,推荐使用pathlib模块
  6. 文件权限:确保有适当的文件读写权限
  7. 文件路径:使用相对路径或绝对路径时要注意跨平台兼容性
  8. 二进制模式:处理非文本文件时使用二进制模式

九、总结

Python的IO操作提供了强大而灵活的文件处理能力,无论是文本文件还是二进制文件,都可以通过简洁的语法进行操作。通过本文的介绍,你应该已经掌握了Python中文件读写、标准输入输出以及相关的高级操作。在实际项目中,合理使用这些IO操作可以帮助你更有效地处理数据和与外部世界交互。