Python语法分析之字符串格式化


Posted in Python onJune 13, 2019

前序

There should be one - and preferably only one - obvious way to do it.
———— the Zen of Python
意译:Python提倡用一种,而且最好是只有一种方法来完成一件事

虽然 Python 有以上的提倡,但却在字符串格式化方面,没有做到这一点。

字符串格式化

敲黑板,划重点:在 Python 中有至少三种常见方式实现字符串格式化:

  1. %-formatting 格式(Python2.6以前,推荐输出时使用)
  2. str.format() 格式(Python2.6,推荐字符串拼接使用)
  3. f-string 格式(Python3.6,推荐使用)

1、printf 风格的字符串格式化(%-formatting 格式)

Python2.6 之前只有这一种方式,使用与 C 中 printf 函数一样的语法。

基础语法:format % value(其中 format 为一个字符串),在 format 中的 % 转换标记符将被替换为零个或者多个 value 条目

基础用法

# coding in Python3.7
print('this is %s blog written in %d%%%02d%%%d %02d:%d:%06.2f' 
  % ('TinyDolphin', 2019, 5, 31, 9, 30, 22.3333))
# this is TinyDolphin blog written in 2019%05%31 09:30:022.33

print('title=%(title)s, author=%(name)s' 
  % {'name': 'TinyDolphin', 'title': 'Python 语法浅析:字符串格式化'})
# title=Python 语法浅析:字符串格式化, author=TinyDolphin

print('%0*.*f' % (6, 2, 2.345))
# 002.35

printf 语法

针对这种格式化操作,重要知识点如下:

1、针对这些转换标记字符,必须按照以下顺序:

    % --> (name) --> '#'、'-'、'0'、'+'、' ' --> m.n | m --> d、s、r、f

2、常用转换类型:

  • %s 格式化字符串(str()函数)
  • %r 格式化字符串(repr()函数)
  •  %d 格式化整数
  • %f 格式化浮点数字,可指定小数点后的精度

3、常用的转换标记字符:

  •  - 用做左对齐
  • + 在正数前面显示加号( + )
  • # 在八进制数前面显示零('0'),在十六进制前面显示'0x'或者'0X'(取决于用的是'x'还是'X')
  • 0 显示的数字前面填充'0',而不是默认的空格
  • % '%%'输出一个单一的'%'
  •  m.n 表示 m 是显示的最小总宽度,n 是小数点后的位数
  •  * 定义宽度或者小数点精度(用在不能预先指定m.n的值)
  •  (var) 映射变量(字典参数)

2、字符串的方式(str.format()格式)

Python2.6 开始,新增了一种格式化字符串的函数 str.format(),它增强了字符串格式化的功能,比如:支持位置映射、关键字映射、对象属性映射、下标映射等多种方式

基本语法是通过 {} 和 : 来代替以前的 %,例如:'%03.2f'被改写成 '{:03.2f}'。

两个格式化方法:

str.format(*args, **kwargs)
    字符串的格式化操作。
    str 包含字符串字面值 AND {} 括起来的替换域。
    每个替换域:位置参数的索引 OR 关键字参数的名称
   
str.format_map(mapping)
    类似于 str.foramt(**mapping)
    不同之处:mapping 会被直接使用而不是复制到一个dict。

PS:Python 存在内置函数 format(value, format_spec):会转换成 type(value).format(value, format_spec)

基础用法

1、按位置访问参数

'{0}-{1}-{2}'.format('a', 'b', 'c')   # 'a-b-c'
'{}-{}-{}'.format('a', 'b', 'c')    # 'a-b-c'
'{2}-{1}-{0}'.format('a', 'b', 'c')   # 'c-b-a'
'{2}-{1}-{0}'.format(*'abc')      # 'c-b-a'

args = ['a', 'b', 'c']
'{2}-{1}-{0}'.format(*args)       # 'c-b-a'

'{0}-{1}-{0}'.format(*['abc', 'def'])  # 'abc-def-abc'

2、按名称访问参数

'{a}-{b}'.format(a='1', b='2')     # '1-2'

kwargs = {'a':'1', 'b':'2'}
'{a}-{b}'.format(**kwargs)       # '1-2'

3、访问参数的属性

class Point:
  def __init__(self, x, y):
    self.x, self.y = x, y
  def __str__(self):
    return 'Point({self.x}, {self.y})'.format(self=self)
    
str(Point(3, 4))            # 'Point(3, 4)'

4、访问参数的项

point = (3, 5)
'X:{0[0]} Y:{0[1]}'.format(point)    # 'X:3 Y:5'

5、替代 %s 和 %r (!s、!r)

'str() = {!s}; repr() = {!r}'.format('a', 'a') # "str() = a; repr() = 'a'"

6、对齐文本以及制定宽度(:<、:^、:>)

'{:<20}'.format('left aligned')     # 'left aligned    '
'{:>20}'.format('right aligned')    # '    right aligned'
'{:^20}'.format('centered')       # '   centered   '
# 使用 '*' 作为填充字符
'{:*^20}'.format('centered')      # '******centered******'

7、替代 %+f、%-f 和 %f 以及指定正负号(:+、:-、:)

'{:+f} {:+f}'.format(3.14, -3.14)    # '+3.140000 -3.140000'
'{: f} {: f}'.format(3.14, -3.14)    # ' 3.140000 -3.140000' 正号—>空格
'{:-f} {:-f}'.format(3.14, -3.14)    # '3.140000 -3.140000' == '{:f} {:f}'

8、替换 %x 和 %o 以及转换基于不同进位制的值(:x、:d、:o、:b)

'int:{0:d} hex:{0:x} oct:{0:o} bin:{0:b}'.format(42)
# 'int:42 hex:2a oct:52 bin:101010'
'int:{0:d} hex:{0:#x} oct:{0:#o} bin:{0:#b}'.format(42)
# 'int:42 hex:0x2a oct:0o52 bin:0b101010'
# '#' : 加上前缀:0x、0o、0b

9、使用逗号作为千位分隔符(:,)

'{:,}'.format(123456789)        # '123,456,789'

10、表示为百分数(:.2%)

'{:.2%}'.format(19/22)         # '86.36%'

11、使用特定类型的专属格式化

import datetime
d = datetime.datetime(2019, 6, 10, 22, 5, 13)
'{:%Y-%m-%d %H:%M:%S}'.format(d)
# '2019-06-10 22:05:13'

12、嵌套参数以及更复杂的示例


3、格式化字符串字面值(f-string 格式)

是带有 'f' 或 'F' 前缀的字符串字面值。

花括号以外的部分按其字面值处理,除了双重花括号 '{{' 或 '}}' 会被替换为相应的单个花括号。

语法如下:

单个花括号 '{',标示一个替换字段(以 Python 表达式打头)
 + 可能有一个以叹号 '!' 标示的转换字符
 + 可能有一个以冒号 ':' 标示的格式说明符
 + 以一个右花括号 '}' 作为结束

注意:格式化字符串字面值中的表达式:

  • 当作正常的 Python 表达式处理 (这一点很重要,也很强大)
  • 不允许空表达式
  • lambda 表达式必须显式地加上圆括号
  • 可以包含换行(例如三引号字符串中)
  • 不能包含注释
  • 从左到右被求值

如果指定了转换符,则表达式求值的结果会先转换再格式化。之后使用 Python 内置函数 format() 进行格式化。

基本用法

name = 'tinyDolphin'
f'my name is {name}'      # 'my name is tinyDolphin'
f'my name is {name!r}'     # "my name is 'tinyDolphin'"

width = 10
precision = 4
value = 12.34567
f'{value:{width}.{precision}}' # '   12.35'

today = datetime.datetime(year=2019, month=6, day=10)
f'{today:%B %d, %Y}'      # 'June 10, 2019'

number = 1024
f'{number:#0x}'         # '0x400'

PS:与 str.format() 有一点不同:在 str.format() 中,非数字索引将自动转化为字符串,而f-strings则不会。

kwargs = {'a':1, 'b':2}
# 使用 str.format()
'a={kwargs[a]}'.format(kwargs=kwargs)  # 'a=1'

# 使用 f-string
f"a={kwargs[a]}"            # × 发生异常
Traceback (most recent call last):
 File "<stdin>", line 1, in <module>
NameError: name 'a' is not defined

# 正确使用 f-string
f"a={kwargs['a']}"           # 'a=1'

总结

从以下三个方面进行对比:

速度上:f-string > %-formatting > str.format()
功能上:f-string > str.format() > %-formatting
可读性: f-string > str.format() > %-formatting

对于速度验证,笔者就不在此进行验证了。

推荐使用场景:

%-formatting:Python2 中,由于其性能优势,在涉及输出的一些操作时,优先推荐使用
str.format():Python2 中,由于其功能优势,在涉及字符串拼接的一些操作时,优先推荐使用
f-string:    Python3 中,强烈推荐使用

好了,以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作具有一定的参考学习价值,谢谢大家对三水点靠木的支持。

Python 相关文章推荐
Python调用C/C++动态链接库的方法详解
Jul 22 Python
Python中函数的用法实例教程
Sep 08 Python
从局部变量和全局变量开始全面解析Python中变量的作用域
Jun 16 Python
Python中Iterator迭代器的使用杂谈
Jun 20 Python
TensorFlow获取加载模型中的全部张量名称代码
Feb 11 Python
Python标准库json模块和pickle模块使用详解
Mar 10 Python
Django Admin 上传文件到七牛云的示例代码
Jun 20 Python
python 获取剪切板内容的两种方法
Nov 28 Python
浅谈Selenium+Webdriver 常用的元素定位方式
Jan 13 Python
Pytorch模型迁移和迁移学习,导入部分模型参数的操作
Mar 03 Python
详细介绍python类及类的用法
May 31 Python
Python内置类型集合set和frozenset的使用详解
Apr 26 Python
pyqt5 从本地选择图片 并显示在label上的实例
Jun 13 #Python
通过pycharm使用git的步骤(图文详解)
Jun 13 #Python
Windows 安装 Anaconda3+PyCharm的方法步骤
Jun 13 #Python
python读取目录下所有的jpg文件,并显示第一张图片的示例
Jun 13 #Python
在Pycharm中使用GitHub的方法步骤
Jun 13 #Python
python 实现在tkinter中动态显示label图片的方法
Jun 13 #Python
windows10下安装TensorFlow Object Detection API的步骤
Jun 13 #Python
You might like
基于mysql的论坛(7)
2006/10/09 PHP
php date与gmdate的获取日期的区别
2010/02/08 PHP
php HtmlReplace输入过滤安全函数
2010/07/03 PHP
ThinkPHP框架里隐藏index.php
2016/04/12 PHP
PHP生成zip压缩包的常用方法示例
2019/08/22 PHP
javascript下有关dom以及xml节点访问兼容问题
2007/11/26 Javascript
原生Javascript封装的一个AJAX函数分享
2014/10/11 Javascript
javascript实现倒计时N秒后网页自动跳转代码
2014/12/11 Javascript
浅谈JSON中stringify 函数、toJosn函数和parse函数
2015/01/26 Javascript
JavaScript的removeChild()函数用法详解
2015/12/27 Javascript
jquery将标签元素的高设为屏幕的百分比
2017/04/19 jQuery
利用JavaScript对中文(汉字)进行排序实例详解
2017/06/18 Javascript
vue.js 实现点击展开收起动画效果
2018/07/07 Javascript
JS中验证整数和小数的正则表达式
2018/10/08 Javascript
实例详解带参数的 npm script
2019/05/28 Javascript
Vue Element UI + OSS实现上传文件功能
2019/07/31 Javascript
Vue中key的作用示例代码详解
2020/06/10 Javascript
Python实现过滤单个Android程序日志脚本分享
2015/01/16 Python
PyQt5实现无边框窗口的标题拖动和窗口缩放
2018/04/19 Python
python:接口间数据传递与调用方法
2018/12/17 Python
Django重置migrations文件的方法步骤
2019/05/01 Python
python求最大公约数和最小公倍数的简单方法
2020/02/13 Python
对Matlab中共轭、转置和共轭装置的区别说明
2020/05/11 Python
初学者学习Python好还是Java好
2020/05/26 Python
浅析几个CSS3常用功能的写法
2014/06/05 HTML / CSS
爱尔兰家电数码商城:Currys PC World爱尔兰
2016/07/23 全球购物
劳力士官方珠宝商:J.R. Dunn Jewelers
2018/09/29 全球购物
英国最大的户外商店:Go Outdoors
2019/04/17 全球购物
模具专业推荐信
2013/10/30 职场文书
作风建设演讲稿
2014/05/23 职场文书
植树造林的宣传标语
2014/06/23 职场文书
诉讼代理人授权委托书
2014/10/11 职场文书
护士个人总结范文
2015/02/13 职场文书
公司表扬信格式
2015/05/04 职场文书
2016年十一促销广告语
2016/01/28 职场文书
一定要知道的 25 个 Vue 技巧
2021/11/02 Vue.js