Skip to content

05 字符串格式化与文件IO

程序要和人交互,就要输出信息;要持久保存数据,就要读写文件。这章讲怎么格式化字符串,怎么读写文件,怎么处理JSON。

一、字符串格式化

1.1 f-string(3.6+)

最推荐的方式,在字符串前加f,花括号里放表达式:

python
>>> name = "World"
>>> f"Hello, {name}!"
'Hello, World!'

>>> year = 2024
>>> f"今年是{year}年"
'今年是2024年'

>>> # 花括号里可以放任意表达式
>>> f"2 + 3 = {2 + 3}"
'2 + 3 = 5'

>>> f"{'hello':>10}"    # 右对齐,宽度10
'     hello'

>>> f"{3.14159:.2f}"    # 保留2位小数
'3.14'

>>> f"{1000000:,}"      # 千位分隔符
'1,000,000'

>>> f"{0.25:.0%}"       # 百分比
'25%'

1.2 str.format()

python
>>> '{}的分数是{}'.format('小明', 95)
'小明的分数是95'

>>> '{1}{0}'.format('世界', '你好')
'你好和世界'

>>> '{name}{count}个'.format(name='苹果', count=3)
'苹果有3个'

>>> # 访问对象属性和索引
>>> coord = (3, 5)
>>> 'X: {0[0]};  Y: {0[1]}'.format(coord)
'X: 3;  Y: 5'

1.3 格式化规格

python
>>> # 对齐
>>> '{:<30}'.format('left aligned')     # 左对齐
'left aligned                   '
>>> '{:>30}'.format('right aligned')    # 右对齐
'                  right aligned'
>>> '{:^30}'.format('centered')         # 居中
'          centered           '

>>> # 数字格式
>>> '{:+f}; {:+f}'.format(3.14, -3.14)  # 带符号
'+3.140000; -3.140000'

>>> '{:,}'.format(1234567890)           # 千位分隔
'1,234,567,890'

>>> '{:.5}'.format('Hello World')       # 截断字符串
'Hello'

>>> # 进制转换
>>> "int: {0:d};  hex: {0:#x};  oct: {0:#o};  bin: {0:#b}".format(42)
'int: 42;  hex: 0x2a;  oct: 0o52;  bin: 0b101010'

1.4 repr()和str()

str()给人看,repr()给机器看:

python
>>> s = 'Hello,\nWorld'
>>> str(s)
'Hello,\nWorld'
>>> print(str(s))
Hello,
World

>>> repr(s)
"'Hello,\\nWorld'"
>>> print(repr(s))
'Hello,\nWorld'

二、读写文件

2.1 open()函数

python
>>> f = open('workfile', 'w', encoding='utf-8')
模式说明
'r'只读(默认)
'w'写入(覆盖)
'a'追加
'r+'读写
'b'二进制模式(如'rb'

2.2 with语句

推荐用with,自动关闭文件:

python
>>> with open('workfile', encoding='utf-8') as f:
...     read_data = f.read()
>>> f.closed
True

即使读取过程中发生异常,with也会保证文件被关闭。

2.3 读取方法

python
>>> with open('workfile', encoding='utf-8') as f:
...     # 读全部内容
...     content = f.read()
...
>>> with open('workfile', encoding='utf-8') as f:
...     # 逐行读取
...     for line in f:
...         print(line, end='')
...
>>> with open('workfile', encoding='utf-8') as f:
...     # 读成列表
...     lines = f.readlines()

2.4 写入方法

python
>>> with open('workfile', 'w', encoding='utf-8') as f:
...     f.write('This is a test\n')
...
15

>>> with open('workfile', 'a', encoding='utf-8') as f:
...     f.write('追加一行\n')

write()返回写入的字符数。写入其他类型需要先转成字符串:

python
>>> value = ('the answer', 42)
>>> s = str(value)
>>> f.write(s)

2.5 文件指针

python
>>> f = open('workfile', 'rb+')
>>> f.write(b'0123456789abcdef')
16
>>> f.seek(5)       # 移到第5个字节
5
>>> f.read(1)
b'5'
>>> f.seek(-3, 2)   # 从末尾倒数第3个
13
>>> f.read(1)
b'd'

seek(offset, whence)——whence为0(默认)从头算,1从当前位置算,2从末尾算。

三、JSON处理

3.1 json.dumps()和json.loads()

Python对象转JSON字符串:

python
>>> import json
>>> data = {'name': 'Alice', 'age': 30, 'scores': [95, 87, 92]}
>>> json.dumps(data, ensure_ascii=False)
'{"name": "Alice", "age": 30, "scores": [95, 87, 92]}'

>>> json.dumps(data, ensure_ascii=False, indent=2)
{
  "name": "Alice",
  "age": 30,
  "scores": [95, 87, 92]
}

JSON字符串转Python对象:

python
>>> json_str = '{"name": "Alice", "age": 30}'
>>> json.loads(json_str)
{'name': 'Alice', 'age': 30}

3.2 读写JSON文件

python
>>> import json
>>> data = {'name': 'Alice', 'age': 30}
>>>
>>> # 写入文件
>>> with open('data.json', 'w', encoding='utf-8') as f:
...     json.dump(data, f, ensure_ascii=False, indent=2)
>>>
>>> # 从文件读取
>>> with open('data.json', encoding='utf-8') as f:
...     data = json.load(f)

dump()/load()直接操作文件对象,dumps()/loads()操作字符串。

3.3 自定义序列化

python
>>> import json
>>> from datetime import datetime
>>>
>>> def default_serializer(obj):
...     if isinstance(obj, datetime):
...         return obj.isoformat()
...     raise TypeError(f"Object of type {type(obj)} is not JSON serializable")
>>>
>>> data = {'time': datetime.now()}
>>> json.dumps(data, default=default_serializer)
'{"time": "2024-01-15T10:30:00.000000"}'

3.4 类型对照

JSONPython
objectdict
arraylist
stringstr
number (int)int
number (real)float
true/falseTrue/False
nullNone

四、总结

功能方法
字符串格式化f-string(推荐)、str.format()
读文件f.read()f.readlines()for line in f
写文件f.write()
自动关闭with open(...) as f
Python→JSONjson.dumps()json.dump()
JSON→Pythonjson.loads()json.load()

f-string最简洁,with语句保证文件关闭,JSON处理用ensure_ascii=False支持中文。