- Python程序设计
- 张雪萍主编
- 4209字
- 2020-08-27 23:59:43
2.8 字符串
本节介绍一个使用频率非常高的数据类型——字符串,它属于不可变序列。
字符串通常用来描述一段文本信息,它只是纯粹的文本,可以包含字符、数字等ASCII编码字符,也可以包含汉字、韩文、日文等Unicode编码字符。
2.8.1 字符串的声明
字符串有3种声明方式:单引号、双引号、三引号(三引号用于声明多行文本)。
1)单引号声明方式
注意:这里输入的是一对单引号,但是里边没有包含任何内容,它的结果就是一个空的字符串。
2)双引号声明方式
当我们直接在交互式提示符下面写“name”时,它以内部呈现的方式显示为单引号,当然这个不影响它最终的结果特性。
如果字符串里面包含单引号,定界符就用双引号,反之亦然。例如:
3)三引号声明方式
在Python中还有一种声明字符串的方法,就是三引号,即左侧三个引号,右侧三个引号,它可以声明一个多行的字符串。假定声明的文本信息不只一行,而是有多行,那么可以直接使用三引号来进行声明(这个三引号不管是单引号还是双引号都可以,只要左右两侧保持一致就行)。
用三引号声明的字符串从表面上来看是为了保存多行信息,但事实上在某些特定的场景有特定的用途,在方法或类定义时它可以作为方法或类成员的一个文档声明信息,出现在帮助文档或帮助信息里。
2.8.2 转义字符
如果一个字符串用双引号或单引号作为定界符,而在引号中又想出现一个特定的单引号或双引号,这时可用称为转义字符的方式来实现。
当在交互式提示符下声明某些特定的变量时,有些字符输入可能会有些麻烦,例如,使用单引号来声明一个变量s,由于单引号声明的时候它不能声明多行字符串,例如:
实际上我们希望网址在下一行输出,但用单引号或双引号声明方式又没办法输入换行符,因此,最后的结果就显示在一行上了,未能达成目标。
如果不用三引号,就使用单引号或双引号,那中间的字符能否换行显示呢?其实也是可以的。通过前面的例子可知,当使用三引号来声明多行字符串的时候,它的换行是通过一个特定的符号“\n”来实现的,所以,“\n”并不是真正在屏幕上出现一个“\n”,它表示一个换行,因此,可以进行如下声明来达到目的。
这里的“\n”是一个特定的或特殊的转义字符,这样的转义字符其实有很多。因为在电脑编码中,有些字符是不打印的,有些是不显示的,还有些有特殊的结构,这些情况都可以使用特定的以“\”开头的某一个转义字符来表示。
通常以反斜线“\”开头的特殊字符表示的是一个转义字符,但这样有时会给字符串的声明带来一定的麻烦,例如,假定现在想表示一个路径:path=“c:\abc\xyz\tag.txt”,命令输入后会报错。
原因在于,当我们在普通的字符串中写上“\”时,它总是和后面的字符形成一个转义字符,即它把“\a”当作一个整体,但它报错的位置并不是“\a”,因为“\a”本身是一个正确的转义字符,系统把“\x”也当作一个转义字符来解释,而转义字符中没有“\x”,因此,系统报错。后面的“\t”是正确的,可当作 “Tab”键来识别。
因此,如果在声明字符串时,字符串中本身就有从左到右的一个反斜线“\”,而且并不想表示转义字符,此时有两种解决办法。
方法一:把反斜线“\”本身使用转义字符来进行声明,即“\\”,前一个“\”表示转义,后一个“\”是真正想出现的字符,这样,最终会出现一个字符“\”。
如果在声明字符串时,输入一个转义字符,很容易出错,那么可以采用下面的方法。
方法二:“r”后跟原始字符串,忽略转义字符。
在字符串前面加一个字符“r”(raw,原始的意思),“r”表示声明,意思是说对于后面出现的“\”,不要当作转义字符来解释,而是真实地出现反斜杠“\”。
这样在声明字符串时,如果不想出现以反斜杠开头的转义字符,那么就在前面加上“r”来忽略转义字符,只形成一个原始的字符串。
转义字符是为了呈现在电脑中无法呈现的,或者在键盘上无法输入的内容的特殊符号。常用转义字符如表2-15所示。
表2-15 常用转义字符
2.8.3 字符串序列通用操作
字符串也是一个序列类型,属于序列中的不可变序列。所以,它不支持类似于列表中的可变操作,但它支持序列的通用操作。
1.str字符串支持序列的通用操作
序列的通用操作如判断元素是否在序列之内、连接序列、重复序列元素、下标获取元素、访问指定索引范围、按步长访问指定索引范围、获取序列长度、获取最小值、获取最大值等都可以用在字符串上。但它不支持可变序列及列表的通用操作,因为它有不可变的特性,即字符串不支持原位改变,也不支持扩展操作。如:
1)返回Unicode编码d对应的单个字符
chr(d):返回Unicode编码d对应的单个字符
【例】 输出Unicode编码从9801开始的10个字符[5]。
2)获取字符的Unicode编码
ord(x):获取字符x的Unicode编码。
字符串不支持可变序列的如删除、修改等操作,但作为字符串本身我们会经常碰到需要反复修改它里面的字符的情况。由于字符串的使用频率非常高,所以Python语言在设计的时候也考虑到了这一点。它可以实现我们想要的目标操作,但是它实现的机制和方法不太一样。在Python标准库里内置了很多方法,可以用在字符串上实现一些多元化的操作。
2.8.4 字符串常用内置方法
假设已经定义了一个字符串s,字符串常用内置方法如表2-16所示。
表2-16 字符串常用内置方法
当然字符串内置的方法还有很多,这里只是列举了一部分。更多方法请使用help命令进行查阅。
关于字符串使用时的几点说明:
1)字符串拼接
假设有如下的字符串 s,发现其倒数第 2 个字符写错了,现在要把它修改正确,可以通过字符串拼接的方法来实现。
尽管不能用原位赋值的方式来进行修改,但是可以按照索引把某一段字符取出来,然后再和其他的字符拼接在一起来达成目标,从而实现替换的功能。
2)字符串的替换方法.replace()
以上通过对字符串切片拼接的方法虽然达成了目标,但这是一种变通的方法,如果要替换的内容比较多,则这种方法的灵活性比较低。这时可以使用字符串自带的“replace()”方法,这个方法是依附于字符串对象的。
它具备两个最基本的参数,第一个是要被替换的旧字符,第二个是替换后的新字符,当然它可以是字符串。看下面的示例。
注意:虽然由 s1='aaaaa'得到了'bbbbb',但字符串 s1 并未改变,原因是字符串本身是不可变序列,它是不能改变的!但可以变通地得到改变后的值,即把改变后的值重新赋值给字符串变量s1,让s1重新指向一个新的对象。
3)拆分、连接方法
还有两个非常常见的操作,就是将字符串按照特定的字符拆分成一个列表,或将一个列表或可迭代的集合用指定的字符连接成一个字符串。第 3 章遍历目录树要频繁地用到这两个方法。
s.split():用于拆分字符串。
s.join():用于将序列中的元素连接成一个字符串,但序列中的元素必须要求是字符串类型的。
join()方法的本意是把一个由字符型数据构成的列表中的元素通过指定的连接符形成一个新的字符串,因此,如果列表中的元素不是字符串类型数据,则不能用此方法进行连接。
split()和join()是非常方便并且在实际开发中使用频率非常高的两个方法。
4)格式化字符串方法
关于字符串有一个非常常用的方法——“format()”,用于格式化字符串。
s.format():用来格式化字符串。
先看它的基本操作。
但这样使用很容易出错,并且这样进行“+”连接的效率也不高,而使用 format()可以更高效。
很显然,将“name”传递给第一个位置、“age”传递给第二个位置、“job”传递给第三个位置,等等。
当然,如果 format()中的参数顺序及占位符都是有规律的,就可以把索引“0、1、2”省略掉,如上面的第二个 print 语句,但不提倡这样,因为如果在同一个位置出现多个结果或在不同的位置出现同一个结果就比较麻烦。但如果带有参数就好办了,如上面的第三个 print 语句,有两个地方都出现了“姓名”,因此,在两个不同的地方都用占位符{0}来表示。这里的占位符{}也称为槽,理解为在需要输出内容的地方事先挖个槽进行占位,所以,有时又把字符串的格式化输出叫作输出的槽机制。槽的内部格式为:
{<参数序号>:<格式控制标记>}
无论是否省略“<参数序号>”,只要有“<格式控制标记>”,就不能省略“:”。“<格式控制标记>”用来控制参数显示时的格式,包括<填充><对齐><宽度><,><精度><类型>6个字段,这些字段是可选的,可以组合使用。
<填充>:用于填充的单个字符。
<对齐>:有3种对齐方式,“<”——左对齐;“>”——右对齐;“^”——居中对齐。
<宽度>:设定的输出宽度。
<,>:数字的千分位分隔符。
<精度>:浮点数小数部分的精度或字符串的最大输出长度。
<类型>:整型(用b、c、d、o、x、X表示),浮点型(用e、E、f%表示)。
说明:只有当输出格式设计得有宽度时才需要考虑对齐和填充的问题!
此外,如果想再输出一个“部门”信息,而事先并没有定义存储“部门”信息的变量,这时可以在 format()参数表中再指定一个变量名称“department”。若之前没有定义这个变量,那么可以在后面括号里的参数中加上“department='tech'”,也能得到想要的结果,即在花括号里可以写上下标索引,也可以写上一个变量。如果花括号里写的是变量,则必须要保证在后面传值的时候给这个变量赋值。
另外,还可以在格式化字符串及前面的占位符中通过添加一些参数或特殊指定的方式给它加上一些高级的语法。这样使用的好处是不需要像拼接一样转换它的类型
其中,{0:10}冒号前面的0表示format()方法中下标索引为0的参数,冒号后面的10表示该参数输出时所占的位数,如果前面{}的顺序与 format()方法中参数的顺序保持一致,那还可以省略掉花括号里冒号前的0和1(但不推荐)。还可通过“>”或“<”来指定右对齐或左对齐,“^”是居中对齐。但请注意:“>”或“<”都要放在冒号的后面。
说明:字符串默认左对齐,数字默认右对齐。
我们经常会碰到将一些数值,特别是浮点型数值进行格式化处理的问题,可以通过格式化字符串的高级语法来指定。
注意:
(1)这样并没有影响原来的值,只是在呈现的时候进行了处理。
(2){:f}和{}都是普通的输出方式,即值是多少直接就输出多少。
(3){:f}输出时在后面加了一个“0”,以保持固定的位数;而{}完全是原样输出。
还可以指定输出数据的宽度,以及按不同进制数据形式来显示,如下:
这里的“{:x},{:o},{:b}”分别表示十六进制数、八进制数、二进制数。还要注意:“{:o}”是小写的字母“o”而不是数字“0”。
以上介绍了字符串的一些常用方法,这些方法可以通过官方文档进行查询[6]或通过help(str)命令进行查询。
以上只介绍了部分字符串方法,当需要更多操作时,我们先不要考虑一些特殊的实现方式,而应该考虑我们正在操作的字符串是不是自带了一些类似的或可以实现当前功能的方法。可以通过查询一些相关的资料和文档来解决问题。