Python 新式格式化方法(.format() 和 f-string),与旧式 % 格式化


🧭 一、Python 字符串格式化的三种主流方式

名称写法示例引入版本特点
旧式格式化"%.2f" % piPython 1.x简洁但功能有限,类似 C 语言
.format() 方法"{:.2f}".format(pi)Python 2.6+更灵活,支持位置、命名、对齐等
f-string(字面量格式化)f"{pi:.2f}"Python 3.6+最简洁、高效、可读性强,现代推荐写法

下面我们重点讲解 新写法(.format() 和 f-string) 的语法,并与 % 对照。


🔧 二、新写法的核心语法:{[name][!r/s/a][:format_spec]}

我们简化为最常用的形式:

{变量名:格式说明}

其中 格式说明(format_spec) 的通用结构是:

[[fill]align][sign][#][0][width][.precision][type]

看起来复杂?别怕!我们只关注你关心的部分:宽度(width)、精度(precision)、类型(type)

对应关系如下:

功能% 写法.format() / f-string 写法
字符串截断 + 宽度%10.5s{:.5s}{:10.5s}
浮点数保留2位小数%.2f{:.2f}
浮点数总宽8位、保留2位%8.2f{:8.2f}
整数补零到5位%05d%.5d{:05d}
左对齐%-10s{: <10}{:<10}

✅ 注意:新写法中,对齐符号是显式的

  • <:左对齐(默认字符串)
  • >:右对齐(默认数字)
  • ^:居中对齐
  • =:符号在前,数字在后(用于正负号)

📚 三、详细对照表 + 示例

1️⃣ 字符串格式化(控制显示长度和宽度)

需求% 写法.format()f-string
显示前5个字符%.5s{:.5s}f"{s:.5s}"
总宽10,右对齐,最多5字符%10.5s{:10.5s}f"{s:10.5s}"
总宽10,左对齐%-10.5s{: <10.5s}{:<10.5s}f"{s:<10.5s}"
s = "Hello, Python!"
print("%10.5s" % s)           # '     Hello'
print("{:10.5s}".format(s))   # '     Hello'
print(f"{s:10.5s}")           # '     Hello'

print("%-10.5s" % s)          # 'Hello     '
print(f"{s:<10.5s}")          # 'Hello     '

2️⃣ 浮点数格式化(控制小数位和总宽度)

需求% 写法f-string
保留2位小数%.2ff"{x:.2f}"
总宽8,保留2位,右对齐%8.2ff"{x:8.2f}"
用0填充,总宽8%08.2ff"{x:08.2f}"
左对齐%-8.2ff"{x:<8.2f}"
x = 3.14159
print("%8.2f" % x)    # '    3.14'
print(f"{x:8.2f}")    # '    3.14'

print("%08.2f" % x)   # '00003.14'
print(f"{x:08.2f}")   # '00003.14'

print("%-8.2f" % x)   # '3.14    '
print(f"{x:<8.2f}")   # '3.14    '

注意:新写法中,0 填充直接写成 08,不需要额外 flag。


3️⃣ 整数格式化(补零、宽度)

需求% 写法f-string
至少5位,不足补0%.5d%05df"{n:05d}"
总宽8,数字至少5位%8.5df"{n:8.05d}" ❌ 不行!
✅ 正确:先保证5位 → f"{n:05d}" 再整体控制宽度需分步或用嵌套
⚠️ 注意:新写法中,不能直接写成 {:8.5d},因为整数没有“精度”概念。
正确做法是:用 0 填充指定宽度即可。
n = 42
print("%.5d" % n)     # '00042'
print(f"{n:05d}")     # '00042'

print("%8.5d" % n)    # '   00042'
print(f"{n:8d}".replace(' ', '0') if len(str(n)) < 5 else ...)  # 复杂!
# 更好的方式:先格式化数字位数,再整体对齐(通常不需要这么复杂)
print(f"{n:05d}".rjust(8))  # '   00042'

💡 实际开发中,整数补零用 {:0Nd} 就够了,很少需要同时控制“数字位数”和“总宽度”。


🆚 四、新旧写法对比总结

维度% 格式化.format() / f-string
可读性较差(符号多)高(结构清晰)
灵活性有限极强(支持命名、表达式、对象属性等)
性能一般f-string 是最快的
错误提示模糊(如类型不匹配报错难懂)更友好
功能扩展不支持自定义格式支持 __format__ 协议
是否推荐❌ 仅用于兼容老代码✅ f-string 是现代 Python 首选

✅ 推荐使用 f-string 的理由:

  • 直接嵌入变量:f"Hello {name}"
  • 支持表达式:f"平方是 {x**2}"
  • 支持格式:f"{price:.2f}"
  • 性能最优(编译时处理)

🧪 五、实战建议:什么时候用哪种?

场景推荐写法
学习/写新项目f-stringf"{x:.2f}"
阅读/维护老代码理解 % 格式
需要动态格式模板(如从配置读取).format()(因为 f-string 不能动态改格式字符串)
简单日志打印f-string 足够

🎁 六、附:常见格式速查表(f-string 版)

x = 123.4567
s = "Python"
n = 42

# 浮点数
f"{x:.2f}"     # '123.46'
f"{x:10.2f}"   # '    123.46'
f"{x:010.2f}"  # '0000123.46'
f"{x:<10.2f}"  # '123.46    '

# 字符串
f"{s:.4s}"     # 'Pyth'
f"{s:>10.4s}"  # '      Pyth'

# 整数
f"{n:05d}"     # '00042'
f"{n:>8d}"     # '      42'