Python
是简洁、易学、面向对象的编程语言。它不仅拥有强大的原生数据类型,也提供了简单易用的控制语句。本节的主要目标是介绍 Python
基础知识,并为接下来的学习奠定基础,本文并非详尽的 Python
教程,但会完整的介绍学习数据结构和算法所需的 Python
基础知识及基本思想,并给出相应的实战示例及解释。
通过本节学习,应掌握以下内容:
python
编程基础Python
的原生数据类型Python
利用输入输出和用户进行交互由于 Python
是一门解释型语言,因此对于简单示例只需要通过交互式会话就能进行学习。通过命令行启动 Python
后,可以看到 Python
解释器提示符为 >>>
:
运行提供的 Python
语句将会返回相应结果。例如, 在命令提示符后使用 print
函数:
>>> print("Data Structures and Algorithms in Python")
>>> Data Structures and Algorithms in Python
但是,我们不能所有程序都在 Python
交互式解释器中一行一行的执行,因此我们需要编写程序文件,例如在文件 hello_world.py
文件中写入以下语句:
print("Data Structures and Algorithms in Python")
使用 python
命令执行该脚本文件:
python hello_world.py
脚本的运行输出结果如下:
Data Structures and Algorithms in Python
除此之外,我们也可以通过诸如 PyChram
和 VSCode
等编辑器运行调试编写完成的 Python
程序。
变量的名字在编程语言中也称标识符,Python
中的标识符以字母或者下划线(_)开头,并且区分大小写( VAR
和 var
表示不同变量)。虽然并非必须,但是为了使代码易于理解和阅读,应当使标识符能够表达变量的含义。
当标识符第一次出现在赋值 (assignment) 语句(变量名=值
)的左侧时,会创建对应的 Python
变量。赋值语句将变量名与值关联起来。Python
会为这个值分配内存空间,然后让这个变量指向这个值,变量存储指向数据的引用,而不是数据本身。当改变变量的值时,Python
会为这个新的值分配另一个内存空间,然后让这个变量指向这个新值。
>>> var = 12.345
>>> var
12.345
>>> var = var + 2
>>> var
14.345
>>> var = False
>>> var
False
赋值语句 var = 12.345
用于创建变量 var
,并且令 var
保存指向数据对象 12.345
的引用。Python 会先计算赋值运算符右边的表达式,然后将指向结果数据对象的引用赋给左边的变量名。如果数据的类型发生改变,例如将布尔值 False
赋值给 var
,则变量 var
的类型也会变成布尔类型。这体现了 Python
的动态特性,即赋值语句可以改变变量的引用,同样的变量可以指向不同类型的数据。
由于 Python
是面向对象编程的编程语言,因此,在 Python
编程语言中,数据同样是对象,而对象是类的实例。类是对数据的构成以及数据所能进行操作的描述,这与抽象数据类型十分类似。
Python
提供 int
和 float
类来实现整数类型和浮点数类型,并包含标准数学运算符(可以通过括号改变运算优先级),如下所示:
运算名 | 运算符 | 解释 |
---|---|---|
加 | + | 加法运算符 |
减 | - | 减法运算符 |
乘 | * | 乘法运算符 |
除 | / | 除法运算符,结果为浮点数 |
幂 | ** | 幂运算符 |
求余 | % | 求余(取模)运算符 |
整除 | // | 整除运算符,与 / 不同,// 会截去小数部分,只返回商的整数部分 |
下面给出整数类型、浮点数类型及运算符的使用示例:
>>> 10 - 5 * 5
-15
>>> (10 - 5) * 5
25
>>> 12.5 * 3.3
41.25
>>> 12 / 2
6.0
>>> 13 / 2
6.5
>>> 13 // 2
6
>>> 3 ** 3
27
>>> 13 % 2
1
Python
通过 bool
类实现布尔数据类型,其可能的状态值包括 True
和 False
,布尔运算符有 and
、or
以及 not
,同时布尔对象也可以用于相等 (==
)、大于 (>
) 等比较运算符的计算结果:
运算名 | 运算符 | 解释 |
---|---|---|
大于 | > | 大于运算符 |
大于等于 | >= | 大于等于运算符 |
小于 | < | 小于运算符 |
小于等于 | <= | 小于等于运算符 |
相等 | == | 相等运算符,判断两个操作数是否相等,如果相等返回 True |
不相等 | != | 不相等运算符,判断两个操作数是否不相等,如果不相等返回 True |
逻辑与 | and | 两个操作数都为 True 时返回 True |
逻辑或 | or | 任意一个操作数为 True 时返回 True |
逻辑非 | not | 对操作数取反,False 变为 True,True 变为 False |
下面给出布尔类型及运算符的使用示例:
>>> True
True
>>> False or True
True
>>> not (True and False)
True
>>> 11 != 111
True
>>> 1024 <= 1024
True
>>> (1024 >=1000) and (1024 <= 1000)
False
除了上述原子数据类型外,Python
还包含许多原生的结构数据类型:1) 有序结构数据类型——列表、字符串以及元;2) 无序结构数据类型——集和与字典。
需要注意的是这里的有序是指在插入的时候,保持插入的顺序性:
>>> # 保持插入的顺序性
>>> list([1,2,3,7,5])
[1, 2, 3, 7, 5]
>>> # 未保持插入的顺序性
>>> set([1,2,3,7,5])
{1, 2, 3, 5, 7}
有序数据结构也可以称为序列。序列在处理系列值时非常有用,例如我们有一个购物清单,如果使用列表来表示(所有元素都放在方括号内,元素间用逗号分隔),形式如下:
>>> shopping = ['cabbage', 'apple', 'beef']
序列可以包含其他序列,例如上示列表中,每个元素就由字符串序列组成,同时列表中也可以包含列表:
>>> shopping = [['cabbage', 2], ['apple', 5], ['beef', ‘50’]]
序列支持一系列 Python
运算,如下所示:
运算名 | 运算符 | 解释 |
---|---|---|
索引 | [] | 获取序列中的某一元素 |
切片 | [:] | 获取序列中的指定部分元素 |
连接 | + | 将序列进行连接 |
重复 | * | 重复序列N次 |
成员 | in | 查询序列中是否含有某一元素 |
成员 | not in | 查询序列中是否不包含某一元素 |
长度 | len | 查询序列的元素个数 |
🔍 索引
序列中的所有的每个元素都有其索引 (indexing),索引是从 0 开始递增的,利用索引就可以访问序列中的每个元素了:
>>> shopping = ['cabbage', 'apple', 'beef']
>>> shopping[0]
'cabbage'
在 Python
中也可以使用负数索引,用于从右向左进行编号,即 -1
是序列最后一个元素的位置,这在我们仅需取序列末尾元素时非常有用:
>>> shopping[-2]
'apple'
序列也可以直接进行索引操作,而无需首先将其赋值给变量:
>>> ['cabbage', 'apple', 'beef'][-1]
'beef'
同样如果函数的返回结果为一个序列,我们也可以直接对其进行索引操作 (关于 input
函数将在 4.1
节详细描述):
>>> example = input('Please enter your name: ')[1]
Please enter your name: alice
>>> example
'l'
🔍 切片
索引的作用是用来访问单个元素,而切片 (slicing) 则可以用于访问序列中指定范围内的元素,切片使用两个冒号分隔的两个索引:
>>> number = [1, 2, 3, 4, 5]
>>> number[1:4]
[2, 3, 4]
>>> number[1:-1]
[2, 3, 4]
从以上示例可以看出,第一个索引指向的元素包含在切片内,第二个索引指向的元素不在切片内。
使用切片语法时,如果省略第二个索引,则切片会取到序列末尾;如果省略第一个索引,则切片会从序列开头开始取;如果两个索引都省略,则会取整个序列:
>>> url = 'https://www.python.org'
>>> sever = url[12:-4]
>>> sever
'python'
>>> domain = url[12:]
>>> domain
'python.org'
>>> protocol = url[:5]
>>> protocol
'https'
>>> copy_url = url[:]
>>> copy_url
'https://www.python.org'
除此之外,切片运算还支持使用步长,即从起点和终点之间每隔若个元素提取一个元素,默认情况下,步长为 1,若步长为负数,即从终点到起点提取元素:
>>> numbers = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
>>>> numbers[0:10:1]
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
>>> numbers[0:10:2]
[0, 2, 4, 6, 8]
>>> numbers[0:6:3]
[0, 3]
>>> numbers[::3]
[0, 3, 6, 9]
>>> numbers[10::-1]
[9, 8, 7, 6, 5, 4, 3, 2, 1, 0]
>>> numbers[10::-2]
[9, 7, 5, 3, 1]
🔍 连接
可使用加法运算符将多个序列连接为一个,但需要注意的是,不同类型的序列不能进行连接:
>>> ['a', 'b', 'c'] + ['d', 'e'] + ['f']
['a', 'b', 'c', 'd', 'e', 'f']
>>> 'Hello ' + 'world!'
'Hello world!'
>>> 'Hello' + ['a', 'b', 'c']
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: can only concatenate str (not "list") to str
🔍 重复
可使用乘法运算符将一个序列重复多次来创建一个新序列:
>>> 'love you!' * 3
'love you!love you!love you!'
>>> [1,2] * 5
[1, 2, 1, 2, 1, 2, 1, 2, 1, 2]
>>> [None] * 5
[None, None, None, None, None]
🔍 成员
使用运算符 in
或 not in
可以检查特定值是否包含或不包含在序列中,并返回指示是否满足的布尔值:满足时返回 True
, 不满足时返回 False
:
>>> names = ['root', 'xiaohui', 'xiaohuihui']
>>> 'root' in names
True
>>> 'hui' in names
False
>>> 'hui' not in names
True
🔍 长度
内置函数len返回序列包含的元素个数:
>>> names = ['root', 'xiaohui', 'xiaohuihui']
>>> len(names)
3
除了可以应用通用的序列操作外,列表有很多特有的方法:
方法名 | 用法 | 解释 |
---|---|---|
index | listA.index(item) | 返回 item 在列表中首次出现的下标 |
count | listA.count(item) | 返回 item 在列表中出现的次数 |
append | listA.append(item) | 在列表末尾添加新元素 item |
extend | listA.extend(listB) | 将列表 listB 附加到列表 listA 末尾 |
insert | listA.insert(i, item) | 在列表的第 i 个位置插入元素 item |
pop | listA.pop(i) | 删除并返回列表中第 i 个位置的元素,如果不指定参数 i,则删除并返回列表中最后一个元素 |
remove | listA.remove(item) | 移除在列表中首次出现的 item |
sort | listA.sort() | 将列表元素排序 |
reverse | listA.reverse() | 将列表元素按相反的顺序排列 |
del | del listA[i] | 删除列表中第 i 个位置的元素 |
clear | listA.clear() | 清空列表 listA 的内容 |
copy | listA.copy() | 复制列表 listA |
1 基本列表操作
接下来将介绍用于创建、修改列表的方法。
🔍 list 函数
使用函数 list
可以将创建空列表或将任何序列转换为列表:
>>> empty_list = list()
>>> []
>>> string_test = list('Python')
>>> string_test
['P', 'y', 't', 'h', 'o', 'n']
range
是一个常见的 Python
函数,它常与列表一起讨论。使用 range
可以生成值序列的范围对象,然后利用 list
函数,能够以列表形式看到范围对象的值,同时也和切片语法类似,其支持使用步长参数:
>>> list(range(10))
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
>>> list(range(1, 10))
[1, 2, 3, 4, 5, 6, 7, 8, 9]
>>> list(range(1, 10, 2))
[1, 3, 5, 7, 9]
🔍 修改列表元素
修改列表只需结合索引使用普通赋值语句即可,使用索引表示法可以修改特定位置的元素:
>>> numbers[0] = 11
>>> numbers
[11, 1, 2, 3, 4, 5, 6, 7, 8, 9]
>>>
使用切片语法可以同时给多个元素赋值,通过使用切片赋值,可将切片替换为长度与其不同的序列,或者插入、删除元素:
>>> fruits = ['apple', 'orange', 'banana', 'pear', 'strawberry']
>>> fruits[2:] = ['lemon', 'watermelon']
>>> fruits
['apple', 'orange', 'lemon', 'watermelon']
>>> fruits[1:1] = ['grape']
>>> fruits
['apple', 'grape', 'orange', 'lemon', 'watermelon']
>>> fruits[1:3] = []
>>> fruits
['apple', 'lemon', 'watermelon']
🔍 删除元素
从列表中删除元素可以使用 del
语句:
>>> fruits = ['apple', 'orange', 'banana', 'pear', 'strawberry']
>>> del fruits[0]
>>> fruits
['orange', 'banana', 'pear', 'strawberry']
>>> del fruits[1:3]
>>> fruits
['orange', 'strawberry']
2 列表方法
方法是与对象紧密联系的函数,方法调用与函数类似,需要在方法名前加上了对象和句点:
object.method(arg)
🔍 index 方法index
方法在列表中查找指定值第一次出现的索引:
>>> fruits = ['apple', 'orange', 'banana', 'pear', 'strawberry']
>>> fruits.index('orange')
1
>>> fruits.index('lemon')
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ValueError: 'lemon' is not in list
查找单词“orange”时,返回其索引 4,但是当搜索列表中不存在的单词“lemon”时,会引发异常。
🔍 count 方法count
方法用于统计指定元素在列表中的数量:
>>> fruits = ['apple', 'orange', 'banana', 'apple', 'orange', ['apple']]
>>> fruits.count('apple')
2
>>> fruits.count(['apple'])
1
🔍 append 方法append
方法用于将一个对象添加到列表末尾:
>>> fruits = ['apple', 'orange', 'banana', 'pear', 'strawberry']
>>> fruits.append('lemon')
>>> fruits
['apple', 'orange', 'banana', 'pear', 'strawberry', 'lemon']
需要注意的是,与其他修改列表的方式类似,append
方法也是原地操作的,它不会返回修改后的新列表,而是直接在旧列表上进行修改。
🔍 extend 元素extend
方法可以在一个列表末尾添加另一个列表,可使用一个列表来扩展原列表:
>>> fruits_1 = ['apple', 'orange']
>>> fruits_2 = ['banana', 'pear']
>>> fruits_1.extend(fruits_2)
>>> fruits_1
['apple', 'orange', 'banana', 'pear']
与拼接运算符 +
不同的是,extend 方法是原地执行的,而 +
会返回得到的新列表,并非原地执行:
>>> fruits_1 = ['apple', 'orange']
>>> fruits_2 = ['banana', 'pear']
>>> fruits = fruits_1 + fruits_2
>>> fruits
['apple', 'orange', 'banana', 'pear']
>>> fruits_1
['apple', 'orange']
🔍 insert 方法insert
方法用于在列表的指定位置插入一个新元素:
>>> fruits = ['apple', 'orange', 'banana', 'pear', 'strawberry']
>>> fruits.insert(2, 'lemon')
>>> fruits
['apple', 'orange', 'lemon', 'banana', 'pear', 'strawberry']
🔍 pop 方法pop
方法用于在列表中删除一个指定位置(默认为最后一个)的元素,并返回这一元素:
>>> fruits = ['apple', 'orange', 'banana', 'pear', 'strawberry']
>>> fruits.pop()
'strawberry'
>>> fruits
['apple', 'orange', 'banana', 'pear']
>>> fruits.pop(1)
'orange'
>>> fruits
['apple', 'banana', 'pear']
🔍 remove 方法remove
方法用于移除在列表中首次出现的指定元素,但列表中之后出现的同样元素,并不会被删除:
>>> fruits = ['apple', 'orange', 'banana', 'apple', 'strawberry', 'apple']
>>> fruits.remove('apple')
>>> fruits
['orange', 'banana', 'apple', 'strawberry', 'apple']
🔍 sort 方法sort
方法用于对列表原地排序,原地排序意味着对原来的列表按顺序排列,而不是返回排序后列表的副本:
>>> x = [1, 3, 4, 9, 8, 2]
>>> x.sort()
>>> x
[1, 2, 3, 4, 8, 9]
由于 sort
修改原列表且不返回任何值,最终的结果列表是经过排序的。如果要获取排序后的列表的副本,而不修改原列表,需使用函数 sorted
:
>>> x = [1, 3, 4, 9, 8, 2]
>>> y = sorted(x)
>>> y
[1, 2, 3, 4, 8, 9]
>>> x
[1, 3, 4, 9, 8, 2]
sorted
方法同样可以用于其他序列,但返回值总是一个列表:
>>> sorted('Hello world!')
[' ', '!', 'H', 'd', 'e', 'l', 'l', 'l', 'o', 'o', 'r', 'w']
🔍 reverse 方法reverse
方法按相反的顺序排列列表中的元素:
>>> x.reverse()
>>> x
[2, 8, 9, 4, 3, 1]
这类似于:
>>> x = [1, 3, 4, 9, 8, 2]
>>> x = x[::-1]
>>> x
[2, 8, 9, 4, 3, 1]
类似的,如果要获取反向排列的列表副本,而不修改原列表,需要使用 reversed
函数:
>>> x = [1, 3, 4, 9, 8, 2]
>>> y = reversed(x)
>>> x
[1, 3, 4, 9, 8, 2]
>>> list(y)
[2, 8, 9, 4, 3, 1]
🔍 clear 方法clear
方法就地清空列表的内容:
>>> x = [1, 3, 4, 9, 8, 2]
>>> x.clear()
>>> x
[]
🔍 copy 方法
我们已经知道 Python
是基于值的管理方式,因此常规复制只是将另一个名称关联到列表,它们指向的是同一个列表,因此修改其中一个列表,另一个也会改变:
>>> fruits = ['apple', 'orange', 'banana', 'strawberry']
>>> fruits_2 = fruits
>>> fruits_2[1] = 'lemon'
>>> fruits
['apple', 'lemon', 'banana', 'strawberry']
copy
方法用于复制列表,区别在于其使两个变量指向不同的列表,将列表 listB
关联到 listA
的副本:
>>> listA = ['apple', 'orange', 'banana', 'strawberry']
>>> listB = listA.copy()
>>> listB[1] = 'lemon'
>>> listA
['apple', 'orange', 'banana', 'strawberry']
Python
没有专门用于表示字符的类型,因此一个字符就是只包含一个元素的字符串。前面介绍了列表的方法,而字符串所拥有的方法要更多,其很多方法都是从模块 string
中“继承”而来的。这里并不会介绍所有字符串的方法,只会介绍一些对于之后数据结构和算法最有用的方法。
方法名 | 用法 | 解释 |
---|---|---|
lower | stringA.lower() | 将字符串中所有字母转换为大写 |
upper | stringA.upper() | 将字符串中所有字母转换为小写 |
count | stringA.count(item) | 返回字符串中 item 出现的次数 |
center | stringA.center(width, fillchar) | 返回长度为 width 的字符串,原字符串居中,fillchar 为填充的字符,fillchar默认值为空格 |
ljust | stringA.ljust(width, fillchar) | 返回长度为 width 的字符串,原字符串靠左,fillchar 为填充的字符,fillchar默认值为空格 |
rjust | stringA.rjust(width, fillchar) | 返回长度为 width 的字符串,原字符串靠右,fillchar 为填充的字符,fillchar默认值为空格 |
find | stringA.find(item) | 返回 item 第一次在字符串中的下标 |
startswith | stringA.startswith(string) | 检查字符串是否以 string 开始,如果是,返回 True,否则返回 False. |
endswith | stringA.endswith | 检查字符串是否以 string 结束,如果是,返回 True,否则返回 False. |
replace | stringA.replace(old, new) | 将指定子串 old 都替换为另一个字符串 new,并返回替换后的结果 |
split | stringA.split(char) | 以 str 为分隔符分割字符串 |
join | string.join(listA) | 返回合并 listA 中元素得到的字符串,以 string 作为合并的分割符 |
🔍 lower 和 upper 方法lower
方法返回字符串的小写版本,而 upper
方法返回字符串的大写版本:
>>> string_1 = 'Hello World!'
>>> string_1.lower()
'hello world!'
>>> string_1.upper()
'HELLO WORLD!'
🔍 count 方法count
方法返回字符串中指定子串出现的次数:
>>> string_2 = 'data structure and algorithms'
>>> string_2.count('a')
4
>>> string_2.count('th')
1
🔍 center、ljust 和 rjust 方法center
、ljust
和 rjust
方法返回一个字符串,原字符串居中 (center) /居左 (ljust) /居右 (rjust),使用指定字符填充新字符串,使其长度为指定的 width
:
>>> string_3 = 'Hello world!'
>>> string_3.center(16, '*')
'**Hello world!**'
>>> string_3.ljust(16, '*')
'Hello world!****'
>>> string_3.rjust(16, '-')
'----Hello world!'
🔍 find 方法find
方法在字符串中查找指定子串,如果找到,就返回第一个找到的子串的第一个字符的索引,否则返回 -1:
>>> string_1 = 'Explicit is better than implicit. Simple is better than complex.'
>>> string_1.find('is')
9
find
方法还支持使用可选参数指定查找的起点和终点,第二个参数指定搜索起点,第三个参数指定搜索终点:
>>> string_1 = 'Explicit is better than implicit. Simple is better than complex.'
>>> string_1.find('is', 10)
41
>>> string_1.find('is', 10, 40)
-1
🔍 replace 方法replace
方法将指定子串都替换为另一个字符串,并返回替换后的结果:
>>> string_1 = 'Hello World!'
>>> string_1.replace('World', 'Python')
'Hello Python!'
🔍 startswith 和 endswith 方法startswith
方法检查字符串是否是以指定字符串开头,endswith
方法检查字符串是否是以指定字符串结尾,是则返回 True,否则返回 False,同时可以通过可选参数在指定范围内检查:
>>> zen_of_python = 'Beautiful is better than ugly. Explicit is better than implicit.'
>>> zen_of_python.startswith('Beautiful')
True
>>> zen_of_python.startswith('Beautiful', 1)
False
>>> zen_of_python.endswith('ugly', 0, 31)
False
>>> zen_of_python.endswith('ugly', 0, 29)
True
🔍 split 方法split
方法用于使用指定分隔符将字符串拆分为序列:
>>> zen_of_python = 'Beautiful is better than ugly. Explicit is better than implicit.'
>>> zen_of_python.split('is')
['Beautiful ', ' better than ugly. Explicit ', ' better than implicit.']
>>> zen_of_python.split()
['Beautiful', 'is', 'better', 'than', 'ugly.', 'Explicit', 'is', 'better', 'than', 'implicit.']
如果没有指定分隔符,默认情况下使用单个或多个连续的空白字符作为分隔符。
🔍 join 方法
与 split
方法相反,join
方法用于使用指定分割符合并序列的元素,并返回合并后的字符串:
>>> ''.join(['1','2','3'])
'123'
>>> fruits = ['apple', 'orange', 'lemon', 'banana']
>>> '--'.join(fruits)
'apple--orange--lemon--banana'
>>> ''.join([1,2,3])
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: sequence item 0: expected str instance, int found
需要注意的是,所合并序列的元素必须都是字符串。
元组与列表非常相似,区别在于,元组和字符串一样是不可修改的。元组的所有元素包含在圆括号内并且以逗号分隔。元组允许使用适用于通用序列的任一操作:
>>> tuple_1 = tuple()
>>> tuple_1
()
>>> tuple_1 = tuple([1,2,3])
>>> len(tuple_1)
3
>>> tuple_1[0:1]
(1,)
>>>
可以使用 tuple
函数创建元素,如果尝试改变元组中的元素,就会导致异常:
>>> tuple_1 = (1,2,3)
>>> tuple_1[1] = 4
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: 'tuple' object does not support item assignment
集合 (set
) 是无序的不重复元素序列,形式为以花括号包含、以逗号分隔的一系列值,可以使用大括号 {}
或者 set()
函数创建集合(创建一个空集合必须用 set()
而不能使用 {}
,因为 {}
是用来创建一个空字典):
>>> setA = {'apple', 'banana', 'lemon'}
>>> setA
{'lemon', 'banana', 'apple'}
>>> setB = set(['apple', 'banana', 'lemon'])
>>> setB
{'lemon', 'banana', 'apple'}
1 基本集合运算
集合支持以下运算:
运算名 | 运算符 | 解释 | ||
---|---|---|---|---|
成员 | in | 查询集合中是否包含指定元素 | ||
成员 | not in | 查询集合中是否不包含指定元素 | ||
长度 | len | 获取集合中元素个数 | ||
setA | setB | 返回 setA 和 setB 的并集 | ||
& | setA & setB | 返回 setA 和 setB 的交集 | ||
- | setA - setB | 返回 setA 和 setB 的差集 | ||
<= | setA <= setB | 查询 setA 是否为 setB 的子集 |
>>> setA = {'apple', 'banana', 'lemon'}
>>> len(setA)
3
>>> 'apple' in setA
True
>>> setB = {'apple', 'banana', 'orange'}
>>> setA | setB
{'banana', 'apple', 'lemon', 'orange'}
>>> setA & setB
{'apple', 'banana'}
>>> setA - setB
{'lemon'}
>>> setB - setA
{'orange'}
>>> setA <= setB
False
>>> setC = {'apple', 'banana'}
>>> setC <= setA
True
2 基本集合方法
集合同样支持一系列方法,其中一些方法具有相对应的运算符,如 union
、intersection
、difference
等:
方法名 | 用法 | 解释 |
---|---|---|
union | setA.union(setB) | 返回 setA 和 setB 的并集 |
intersection | setA.intersection(setB) | 返回 setA 和 setB 的交集 |
difference | setA.difference(setB) | 返回 setA 和 setB 的差集 |
issubset | setA.issubset(setB) | 查询 setA 是否为 setB 的子集 |
add | setA.add(item) | 向 setA 添加元素 item |
remove | setA.remove(item) | 从集合 setA 中移除 item |
pop | setA.pop() | 随机移除 setA 中的一个元素 |
clear | setA.clear() | 清空 setA 中的所有元素 |
🔍 union、intersection、difference 与 issubset 方法union
、intersection
、difference
与 issubset
方法分别对应于集合运算符 |
、&
、-
和 <=
:
>>> setA = {'lemon', 'banana', 'apple'}
>>> setB = {'banana', 'apple', 'orange'}
>>> setA.union(setB)
{'banana', 'apple', 'lemon', 'orange'}
>>> setA.intersection(setB)
{'apple', 'banana'}
>>> setA.difference(setB)
{'lemon'}
>>> setA.issubset(setB)
False
🔍 add 方法add
方法用于向集合中添加元素:
>>> setA = {'lemon', 'banana', 'apple'}
>>> setA.add('orange')
>>> setA
{'lemon', 'banana', 'apple', 'orange'}
>>> setA.add('apple')
>>> setA
{'lemon', 'banana', 'apple', 'orange'}
🔍 remove 方法remove
方法用于从集合中移除指定元素:
>>> setA = {'lemon', 'banana', 'apple', 'orange'}
>>> setA.remove('apple')
>>> setA
{'lemon', 'banana', 'orange'}
>>> setA.remove('apple')
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
KeyError: 'apple'
从上示例可以看出,使用 remove
方法时当元素不存在,则会引发错误。
🔍 pop 方法pop
方法用于从集合中移除随机元素,并且返回值为移除的元素:
>>> setA = {'banana', 'apple', 'lemon', 'orange'}
>>> setA.pop()
'banana'
>>> setA
{'apple', 'lemon', 'orange'}
🔍 clear 方法clear
方法用于清空集合:
>>> setA
{'apple', 'lemon', 'orange'}
>>> setA.clear()
>>> setA
set()
字典由键及其相应的值组成,每个键-值
对称为一项 (item
)。在以下示例中,键为水果名,而值为价格。整个字典放在花括号内,每个键与其值之间都用冒号 (:
) 分隔,项之间用逗号分隔,空字典用 {}
表示:
>>> fruits = {'apple': 5.0, 'orange': 3.5, 'banana': 2}
>>> fruits
{'apple': 5.0, 'orange': 3.5, 'banana': 2}
需要注意的是,字典并不是根据键来进行有序维护的,键的位置是由散列来决定的。
1 基本字典运算
字典的基本运算符如下表所示:
运算名 | 运算符 | 解释 |
---|---|---|
[] | dictA[key] | 返回与键 key 相关联的值,如果没有则报错 |
in | key in dictA | 如果字典中包含键 key,返回 True,否则返回 False |
not in | key not in dictA | 如果字典中不包含键 key,返回 True,否则返回 False |
del | del dictA[key] | 从字典dictA中删除 key 对应的键-值对 |
🔍 创建字典
可使用函数 dict
从其他映射或键-值对序列创建字典:
>>> fruits = [('apple', 5.0), ('orange', 3.5)]
>>> d_fruits = dict(fruits)
>>> d_fruits
{'apple': 5.0, 'orange': 3.5}
同样也可以通过实参来调用 dict
函数:
>>> d_fruit = dict(apple=5.0,orange=3.5)
>>> d_fruit
{'apple': 5.0, 'orange': 3.5}
字典中的键可以是任何不可变的类型,如实数、字符串或元组,但不能是列表,因为列表是可变类型。
🔍 访问字典中的值
访问字典的语法与访问序列的语法十分相似,只不过是使用键来访问,而不是下标:
>>> fruits = {'apple': 5.0, 'orange': 3.5, 'banana': 2}
>>> fruits['apple']
5.0
字典中同样可以使用成员运算符,但表达式 key in dictA
或 key not in dictA
(其中 dictA
是一个字典)查找的是键而不是值:
>>> fruits = {'apple': 5.0, 'orange': 3.5, 'banana': 2}
>>> 5.0 in fruits
False
>>> 'apple' in fruits
True
len(dictA)
返回字典 dictA
中包含的项(键-值对)数:
>>> fruits = {'apple': 5.0, 'orange': 3.5, 'banana': 2}
>>> len(fruits)
3
🔍 修改字典元素
修改字典中的元素,可以使用 d[key] = value
将值 value
关联到键 key
上,如果字典中原本没有的键 key
,将会在字典中创建一个新项:
>>> fruits = {'apple': 5.0, 'orange': 3.5, 'banana': 2}
>>> fruits['apple'] = 5.5
>>> fruits
{'apple': 5.5, 'orange': 3.5, 'banana': 2}
>>> fruits['lemon'] = 6.0
>>> fruits
{'apple': 5.5, 'orange': 3.5, 'banana': 2, 'lemon': 6.0}
🔍 删除字典元素del dictA[key]
用于删除键为 key
的项:
>>> fruits = {'apple': 5.0, 'orange': 3.5, 'banana': 2}
>>> del fruits['apple']
>>> fruits
{'orange': 3.5, 'banana': 2}
2 基本字典方法
与其他内置类型一样,字典也有其特有方法:
方法名 | 用法 | 解释 |
---|---|---|
get | dictA.get(key, alt) | 返回字典 dictA 中 key 对应的值,如果没有则返回 alt,如果不指定 alt 则返回值为 None |
keys | dictA.keys() | 返回字典 dictA 中所有键 |
values | dictA.values() | 返回字典 dictA 中所有值 |
items | dictA.items() | 返回字典 dictA 中所有键–值对 |
🔍 get 方法get
方法的存在,可以弥补访问字典中没有的项时引发错误的问题:
>>> fruits = {'apple': 5.0, 'orange': 3.5, 'banana': 2}
>>> fruits['lemon']
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
KeyError: 'lemon'
>>> print(fruits.get('lemon'))
None
如上所示,使用get来访问不存在的键时,并不会引发异常,而是返回None
,可以通过使用可选参数,在访问的键不存在时返回指定的值而不是None
:
>>> print(fruits.get('lemon', 4.0))
4.0
🔍 keys、values 和 items 方法
items
方法返回一个包含所有字典项的列表(也称为字典视图),其中每个元素都为 (key, value)
的形式;keys
方法返回一个包含字典中的所有键的字典视图;values
方法返回一个由字典中的值组成的字典视图:
>>> fruits = {'apple': 5.0, 'orange': 3.5, 'banana': 2}
>>> fruits.keys()
dict_keys(['apple', 'orange', 'banana'])
>>> fruits.values()
dict_values([5.0, 3.5, 2])
>>> fruits.items()
dict_items([('apple', 5.0), ('orange', 3.5), ('banana', 2)])
程序常常需要与用户进行交互,以获得用户提交的数据。Python
提供了input
函数,它接受用户输入数据并且返回一个字符串的引用。input
函数接受一个字符串作为参数,该字符串用于作为提示用户输入的文本,因此也被称为提示字符串:
>>> number = input('Enter the number of students: ')
Enter the number of students: 52
>>> number
'52'
在交互式解释器中执行第一行 number = input('Enter the number of students: ')
,它打印字符串 "Enter the number of students: "
,提示用户输入相应的信息。此处输入 52
并按回车,获取用户在提示字符串后的输入后,存储在 number
变量中。需要注意的是 input
函数返回的值是字符串类型,如果需要将这个字符串转换成其他类型,必须提供相应的类型转换,以进行所需操作:
>>> score = input('Enter the total score: ')
Enter the total score: 4396
>>> number = input('Enter the number of students: ')
Enter the number of students: 52
>>> average_score = int(score) / int(number)
>>> average_score
84.53846153846153
我们在以上示例中,已经不止一次看到了 print
函数,其提供了非常简便打印 Python
输出的方法。它接受零个或者多个参数,默认使用单个空格作为分隔符来显示结果,可以通过可选参数 sep
修改分隔符。此外,默认情况下每一次打印都以换行符结尾,可以通过设置参数 end
来改变:
>>> print('Data', 'Structure', 'and', 'Algorithms')
Data Structure and Algorithms
>>> print('Data', 'Structure', 'and', 'Algorithms', sep='-')
Data-Structure-and-Algorithms
>>> print('Data', 'Structure', 'and', 'Algorithms', sep='-', end='!!!')
Data-Structure-and-Algorithms!!!>>>
格式化字符串是一个模板,其中包含保持不变的单词或空格,以及用于之后插入的变量的占位符。 使用格式化字符串,可以根据运行时变量的值而发生改变:
print("The price of %s is %d yuan." % (fruit, price))
%
是字符串运算符,被称作格式化运算符。 表达式的左边部分是模板(也叫格式化字符串),右边部分则是一系列用于格式化字符串的值,右边的值的个数与格式化字符串中 %
的个数一致。这些值将依次从左到右地被换入格式化字符串。
格式化字符串可以包含一个或者多个转换声明。转换字符告诉格式化运算符,什么类型的值会被插入到字符串中的相应位置。在上面的例子中,%s
声明了一个字符串,%d
声明了一个整数。下表总结了所有的类型声明:
类型声明 | 输出格式 |
---|---|
d、i | 整数 |
u | 无符号整数 |
f | m.dddd 格式的浮点数 |
e | m.dddde±xx 格式的浮点数 |
E | m.ddddE±xx 格式的浮点数 |
g | 对指数小于 -4 或者大于 5 的数使用%e,否则使用%f |
c | 单个字符 |
s | 字符串 |
可以在 %
和格式化字符之间加入一个格式化修改符,用于实现更加复杂的输出格式:
修改符 | 示例 | 解释 |
---|---|---|
数字 | %10d | 将值居中放在 10 个字符宽的字符串中 |
- | %-10d | 将值左对齐放在 10 个字符宽的字符串中 |
+ | %+d | 在数字前显示符号 |
0 | %010d | 将值放在 10 个字符宽的字符串中,并在前面补 0 |
. | %10.3f | 将值放在 10 个字符宽的字符串中,并且保留小数点后 2 位 |
(name) | %(name)d | 从字典中获取 name 键对应的值 |
>>> print("The price of %s is %d yuan." % ('apple', fruits['apple']))
The price of apple is 5 yuan.
>>> print("The price of %s is %10d yuan." % ('apple', fruits['apple']))
The price of apple is 5 yuan.
>>> print("The price of %s is %+10d yuan." % ('apple', fruits['apple']))
The price of apple is +5 yuan.
>>> print("The price of %s is %-10d yuan." % ('apple', fruits['apple']))
The price of apple is 5 yuan.
>>> print("The price of %s is %10.3f yuan." % ('apple', fruits['apple']))
The price of apple is 5.000 yuan.
>>> print("The price of apple is %(apple)f yuan." % fruits)
The price of apple is 5.000000 yuan.
上述方式虽然依旧可以使用,但是目前推荐到的另一种解决方案是模板字符串 format
,其旨在简化基本的格式设置机制,它融合并强化了前一方法的优点。使用 format
格式化函数时,每个替换字段使用花括号括起,其中可以包含变量名,替换字段也可以没有名称或将索引用作名称::
>>> "The price of {} is {} yuan.".format('apple', 5.0)
'The price of apple is 5.0 yuan.'
>>> "The price of {fruit} is {price} yuan.".format(fruit='apple', price=price)
'The price of apple is 5.0 yuan.'
>>> "The price of {1} is {0} yuan.".format(5.0, 'apple')
'The price of apple is 5.0 yuan.'
从上述示例可以看出,索引和变量名的排列顺序无关紧要。除此之外,还通过结合冒号 :
,从而利用格式说明符(与 %
运算符类似):
格式 | 示例 | 输出 | 解释 |
---|---|---|---|
{:.2f} | ‘{:.2f}’.format(2.718281) | 2.72 | 保留两位小数 |
{:+.2f} | ‘{:+.2f}’.format(2.718281) | +2.72 | 带符号保留两位小数 |
{:0>10.2f} | ‘{:0>10.2f}’.format(2.718281) | 0000002.72 | 左对齐,数字左边补零至宽度为10,原数字保留两位小数 |
{:0<10.2f} | ‘{:0<10.2f}’.format(2.718281) | 2.72000000 | 右对齐,数字右边补零至宽度为10,原数字保留两位小数 |
{:0^10.2f} | ‘{:0^10.2f}’.format(2.718281) | 0002.72000 | 居中对齐,数字两侧补零至宽度为10,原数字保留两位小数 |
{:,} | ‘{:,}’.format(100000) | 100,000 | 以逗号分隔的数字格式 |
{:.2%} | ‘{:.2%}’.format(2.718281) | 271.83% | 百分比格式 |
{:.4e} | ‘{:.4e}’.format(2.718281) | 2.7183e+00 | 指数计数法 |
>>> value = 2.718281828459045
>>> '{} is approximately {:.2f}'.format('e', value)
'e is approximately 2.72'
>>> '{} is approximately {:+.2f}'.format('e', value)
'e is approximately +2.72'
>>> '{} is approximately {:0>10.2f}'.format('e', value)
'e is approximately 0000002.72'
>>> '{} is approximately {:0<10.2f}'.format('e', value)
'e is approximately 2.72000000'
>>> '{} is approximately {:^10.2f}'.format('e', value)
'e is approximately 2.72 '
>>> '{:,}'.format(100000)
'100,000'
>>> '{} is approximately {:.2%}'.format('e', value)
'e is approximately 271.83%'
>>> '{} is approximately {:.4e}'.format('e', value)
'e is approximately 2.7183e+00'
>>> '{} is approximately {:0=+10.2f}'.format('e', value)
'e is approximately +000002.72'
从上述示例中,很容易总结出,使用 :
号可以指定宽度、精度以及千位分隔符等,^
、<
、>
分别用于居中、左对齐、右对齐,并且其后可以指定宽度, 并可以使用指定单个字符进行填充,默认情况下用空格填充,也可以使用说明符 =
,指定将填充字符放在符号和数字之间。
同样我们可以使用 b
、d
、o
、x
进行数据类型转换,分别是二进制、十进制、八进制、十六进制,c
用于将数据转换为 Unicode
码:
>>> "The number is {num:b}".format(num=1024)
'The number is 10000000000'
>>> "The number is {num:d}".format(num=1024)
'The number is 1024'
>>> "The number is {num:o}".format(num=1024)
'The number is 2000'
>>> "The number is {num:x}".format(num=1024)
'The number is 400'
>>> "The number is {num:c}".format(num=1024)
'The number is Ѐ'
版权说明 : 本文为转载文章, 版权归原作者所有 版权申明
原文链接 : https://blog.csdn.net/LOVEmy134611/article/details/121192755
内容来源于网络,如有侵权,请联系作者删除!