1、列表(list)与元组(tuple)
列表和元组都是可以放置任意数据类型的有序集合
l = [1, 2, 'hello', 'word']
tup = ('jack', 22)
1.1 列表与元组的特点
(1)列表是动态增长的,长度大小不固定,可以随意地增加、删除或者改变元素;
(2)元组是静态的,长度大小固定,无法增加、删除或者改变。
1.1.1 存储方式的差异
(1)列表在存储数据的时候,需要存储指针来指向对应的元素,同时需要额外存储已经分配的长度大小,从而实时追踪列表空间的使用情况,当空间不足时可以及时分配额外空间。这样的机制保证了其操作的高效性,减小了每次增加/删除操作时空间分配的开销,增加/删除的时间复杂度均为O(1);
(2)元组的存储空间是固定的。
1.1.2 列表与元组的性能
(1)从存储方式的区别看出,元组比列表更加轻量级,总体上元组的性能要略优于列表;
(2)python在后台会对静态数据做一些资源缓存(resource caching)。通常来说,因为垃圾回收机制的存在,如果一些变量不被使用了,python就会回收它们所占用的内存,返还给操作系统,以便其他变量或应用使用。但对于一些静态变量,比如元组,如果它不被使用并且占用空间不大时,python会这暂时缓存这部分内存,这样下次再创建同样大小的元组时,就可以直接分配之前缓存的内存空间,这样就能大大加快程序的运行速度;
(3)如果想要增加、删除或改变元素,那么显然列表更优
1.1.3 二者的使用场景
(1)如果存储的数据和变量不变,元组比较适合;
(2)如果存储的数据和变量是可变的,列表更适合。
1.2 操作列表
1.2.1 列表的创建
创建一个空列表
empty_list = list()
# []是一个内置的c函数,可以直接被调用,效率比较高
empty_list = []
1.2.2 访问列表
(1)通过索引或切片来访问列表的元素,索引从0开始
变量名[索引]
(2)返回元素出现的次数
变量名.count(元素值)
(3)返回元素的索引
变量名.index(元素值)
1.2.3 修改、添加和删除元素
(1)修改
变量名[索引] = <元素值>
(2)添加
# 在列表末尾添加元素
变量名.append(元素值)
# 在列表中插入元素,相当于将列表中既有的元素都右移一个位置
变量名.insert(索引,元素值)
(3)删除
# 删除原列表中的元素,不可复用
del 变量名[索引]
# 逻辑列表中的元素,可以赋用,默认删除最后一个元素
变量名.pop(索引)
# 根据值删除元素,只删除列表中第一个出现的值,可以赋用
变量名.remove(元素值)
1.2.4 排序
# 永久性排序,默认从小到大(字母一样),相反顺序需要传递参数reverse=True
变量名.sort()
# 临时排序,不改变原有顺序
变量名.sorted()
# 倒着打印列表
变量.reverse()
1.2.4 遍历列表
# 遍历列表/元组中的每个元素
for 临时变量 in 列表变量:
循环语句
1.2.5 列表解析
列表变量 = [含临时变量的表达式 for 临时变量 in range()]
示例:squares = [value**2 for value in range(1,11)]
输出:[1,4,9,16,25,36,49,64,81,100]
1.3 操作元组
对已有的元组做任何修改,只能重新开辟一块内存,创建新的元组
1.3.1 增加元素
tup = (1, 2, 3, 4)
new_tup = tup + (5, )
new_tup
(1, 2, 3, 4, 5)
1.3.2 访问元组
类似于列表
1.3.3 排序
只有sorted()和reversed()函数
2、字典(dict)和集合(set)
(1)字典是一系列键值对组成的元素的集合,在python3.7+被确认为有序,长度大小可变,元素可以任意地删减和改变,相比于列表和元组性能更优,特别是对于查找、添加和删除操作,都能在常数时间复杂度内完成;
(2)集合和字典基本相同,唯一的区别就是集合没有键值对,是一系列无序的、唯一的元素组合。
(3)字典的内部组成是一张哈希表,可以直接通过键的哈希值找到对应的值,用字典存储数据进行查找时,只需O(1)的时间复杂度即可完成;集合是高度优化的哈希表,里面元素不能重复,其添加和查找操作只需O(1)的复杂度
2.1 字典和集合的创建
无论是键还是值,都可以是混合类型
字典:
d1 = {}
d1 = {'name': 'jack', 'age': 20, 'gender': 'male'}
d1 = dict({'name': 'jack', 'age': 20, 'gender': 'male'})
d1 = dict([('name', 'jack'), ('age', 20), ('gender', 'male')])
d1 = dict(name='jack', age=20, gender='male')
集合:
s1 = {1, 'hello', 3.0}
s2 = set([1, 'hello', 3.0])
2.2 元素的访问
(1)字典默认直接访问键,如果不存在则抛出异常
示例:
d = {'name': 'jason', 'age': 20}
d['name']
结果:'jason'
(2)通过get(key,default)函数进行索引,如果不存在,返回一个默认值
示例:
d = {'name': 'jason', 'age': 20}
d.get('name')
d.get('jack', 'null')
结果:
'jason'
'null'
(3)集合并不支持索引操作,其本质是一个哈希表,判断元素是否在字典或集合内可以用value in dict/set
2.3 增加、删除、更新
字典:
示例:
d = {'name': 'jason', 'age': 20}
d['gender'] = 'male'
d['dob'] = '1998-01-01'
# 更新键'dob'对应的值
d['dob'] = '1998-02-02'
# 删除键'dob'对应的元素对
d.pop('dob')
集合:
s = {1, 2, 3}
# 增加元素4到集合
s.add(4)
# 删除元素1,集合的pop()操作时删除集合最后一个元素
s.remove(1)
2.4 遍历
字典: 遍历字典时,默认遍历所有的键
(1)遍历所有的键值对
for 临时变量1, 临时变量2 in 字典变量.items():
循环语句
(2)遍历所有的键(不加.keys()默认遍历键)
for 临时变量 in 字典变量.keys():
循环语句
(3)遍历所有的值
for 临时变量 in 字典变量.values():
循环语句
2.5 排序
用sorted()可以对键进行排序
3、字符串
字符串是由独立字符组成的一个序列,通常包含在单引号,双引号,三引号中
3.1 字符串的操作
(1)字符串支持索引操作,遍历字符串相当于遍历字符串中的每个字符,字符串本身是不可变的,但是可以通过.replace(‘目标字符’, ‘替换字符’),也可以通过’+‘进行拼接,每次想要改变字符串,往往需要O(n)的时间复杂度,n为新字符串的长度
(2)操作符’+='进行字符串拼接
# 表示str1 = str1 +str2
str1 += str2
示例:
s =' '
for n in range(0,100000):
s += str(n)
每次处理字符串拼接操作时,python首先会检测str1还有没有其他引用,如果没有,就会尝试原地扩充字符串缓冲区的大小,而不是重新分配一块内存来创建新的字符串拷贝,这样的话上述例子时间复杂度就仅为O(n)了,所以使用此操作符进行字符串拼接,不用过分担心效率问题了
(3)字符串内置join函数,string.join(iterable)进行拼接
l = []
for n in range(0,100000):
l.append(str(n))
l = ' '.join(l)
由于列表的append操作是O(1)复杂度,字符串同理,因此上述例子时间复杂度为n*O(1)=O(n)
# join函数与map函数结合,效率更高
s = " ".join(map(str, range(0,100000)))
(4)字符串分割函数split()
# 按照separator进行分割
string.split(separator)
(5)string.strip(str)去掉首位的str字符串
3.2 字符串的格式化
(1)sting.format()方法进行字符串格式化
#槽的顺序和format()函数中参数的顺序默认情况下一一对应,都是从0开始
"{}:计算机{}的CPU占用率为{}%".format("2018-10-10","C","10")
把format()方法中的参数按对应顺序填充到模板字符串的槽中,可以在槽中指定所要填充的format()中第几个参数
(2)槽内部对格式化的配置
–{<参数序号>:<格式控制标记>}
–{:<填充><对齐><宽度>},填充是用于填充的单个字符,对齐包括左对齐<,右对齐>,居中^,宽度是指槽设定的输出宽度
–{:<,><.><类型>},第一个尖括号中的逗号为数字的千位分隔符,第二个尖括号中的点表示浮点数小数精度或字符串最大输出长度,类型包括整数b,c,d,o,x,X,浮点数包括E,e,f,%
例:"{0:=^20}".format("P") 输出为’========P========’
"{:10}".format("p") 输出为’p_________’ #默认情况下填充为空格左对齐
4、条件与循环
(1)在条件语句中,if可以单独使用,if条件语句的判断,除了boolean类型外,其他最好显示出来
(2)可以通过range()函数拿到索引,然后再遍历元素
示例:
l = [1, 2, 3, 4, 5]
for index in range(0, len(l)):
if index < 5:
print(l[index])
输出:
1
2
3
4
5
(3)同时需要 索引和元素时,可以通过内置函数enumerate(),用它来遍历集合,不仅返回每个元素,还返回其对应的索引
示例:
l = [1,2,3,4,5,6,7]
for index, item in enumerate(l):
if index < 5:
print(item)
结果:
1
2
3
4
5
(4)countinue,跳出当前这层循环,继续执行下面的循环;break跳出所在的整个循环体
(5)如果遍历已知的集合,找出满足条件的元素,并进行相应操作,那么for循环相对简洁些;如果在满足某个条件前,不停地重复某些操作,并且没有特定的集合需要去遍历,一般会使用while循环
4.1条件与循环的复用
语法1:
expression1 if condition else expression2 for item in iterable
相当于:
for item in iterable:
if condition:
expression1
else:
expression2
语法2:
expression for item in iterable if condition
语法3:
[(xx,yy) for xx in x for yy in y if xx != yy]
相当于:
l = []
for xx in x:
for yy in y:
if xx != yy:
l.append((xx, yy))
5、异常处理
(1)在执行程序的时候,如果某处抛出了异常,程序就会被终止并退出,异常处理就是即使遇到了异常,也可以不终止程序,让其继续运行下去。通常使用try和except来解决。
**示例:**
try:
s = input('please enter two numbers separated by comma: ')
num1 = int(s.split(',')[0].strip())
num2 = int(s.split(',')[1].strip())
...
except (ValueError, IndexError) as err:
print('Error: {}'.format(err))
print('continue')
...
**或者:**
try:
s = input('please enter two numbers separated by comma: ')
num1 = int(s.split(',')[0].strip())
num2 = int(s.split(',')[1].strip())
except ValueError as err:
print('Value Error: {}'.format(err))
except IndexError as err:
print('Index Error: {}'.format(err))
print('continue')
(2)可以用Exception匹配任意非系统异常,也可以在except后面省略异常类型,表示与任意异常相匹配,包括系统异常。
示例:
try:
s = input('please enter two numbers separated by comma: ')
num1 = int(s.split(',')[0].strip())
num2 = int(s.split(',')[1].strip())
except ValueError as err:
print('Value Error: {}'.format(err))
except IndexError as err:
print('Index Error: {}'.format(err))
except Exception as err:
print('Other Error: {}'.format(err))
print('continue')
或者:
try:
s = input('please enter two numbers separated by comma: ')
num1 = int(s.split(',')[0].strip())
num2 = int(s.split(',')[1].strip())
except ValueError as err:
print('Value Error: {}'.format(err))
except IndexError as err:
print('Index Error: {}'.format(err))
except:
print('Other Error')
print('continue')
(3)异常处理后外加finally,即无论发生什么异常,finally里的语句都会被执行,比如文件打开后关闭