05 Python 元组:不可变序列的解析和应用

前言

在 Python 编程领域,元组(Tuple)是一类极为重要的数据结构。它属于不可变的序列类型,通过圆括号 () 进行定义,其中元素可涵盖多种不同数据类型,元素间以逗号分隔。元组凭借其独特性质,在诸多编程场景中发挥着关键作用。

元组定义

元组中的元素依照特定顺序构建起序列,具备有序性这一显著特征,我们能够借助索引便捷地访问其中元素。与列表存在本质区别的是,元组属于不可变类型。这表明一旦定义元组类型的变量,其中元素便无法再进行修改,元素的值也固定不可变动。这种不可变性在保障数据稳定性与安全性方面具有重要意义。

元组的运算

索引操作

元组支持通过索引精准访问元素

t = (10, 20, 30, 40, 50)
print("元组t的第一个元素:", t[0]) # 输出:10,
print("元组t的最后一个元素:", t[-1]) # 输出: 50

正向索引从0开始,负向索引从-1开始,通过索引可以定位元组中的元素

切片操作

切片操作能够帮助我们获取元组的特定片段

t = (10, 20, 30, 40, 50)
print("获取索引1到3的元素:", t[1:3]) # 输出:(20,30)
print("从索引2开始到末尾的元素:", t[2:]) # 输出:(30,40,50)
print("获取整个元组:", t[:]) # 输出:(10,20,30,40,50)
print("步长为2获取元素:", t[::2]) # 输出:(10,30,50)

切片操作通过指定起始索引、结束索引(不包含该索引对应元素)以及步长,灵活截取元组片段。

连接和重复运算

元组之间可进行连接和重复运算

t1 = (1, 2, 3)
t2 = (4, 5, 6)

print("连接元组t1和t2:", t1 + t2) # 输出:(1,2,3,4,5,6)
print("元组t1重复3次:", t1 * 3) # 输出:(1,2,3,1,2,3,1,2,3)

连接运算将两个元组合并为一个新元组,重复运算则按照指定次数复制元组元素

循环遍历元组中的元素

我们可使用for循环遍历元组中的元素。

t1 = (35, 12, 98)
for elem in t1:
    print(elem)

输出:
35
12
98
通过循环,可依次访问元组中的每个元素,便于对元组数据进行处理。

成员运算

利用innot in关键字可判断元素是否存在于元组中。

t1 = (1, 2, 3)
t2 = (4, 5, 6)
print("判断1是否在元组t1中:", 1 in t1) # 输出:True
print("判断7是否不在元组t2中:", 7 not in t2) # 输出:True

内置函数运算

t3 = (10, 20, 30, 40, 50)
print("元组t3的长度:", len(t3)) # 输出:5
print("元组t3中的最大值:", max(t3)) # 输出:50
print("元组t3中的最小值:", min(t3)) # 输出:10
print("元组t3中所有元素的和:", sum(t3)) # 输出:150

打包和解包操作

在Python中,存在打包和解包这两种特殊操作。当将多个逗号分割的值赋给一个变量是,这些值会自动打包成一个元组类型;而将一个元组赋值给多个变量时,元组会解包成多个值并分别赋给对应的变量

# 打包操作
a = 1, 10, 100
print(type(a))  # <class 'tuple'>
print(a)        # (1, 10, 100)
# 解包操作
i, j, k = a
print(i, j, k)  # 1 10 100

在解包过程中,若解包出来的元素个数与变量个数不匹配,会触发ValueError异常,错误信息分别为too many values to unpack(解包的值太多)或not enough values to unpack(解包的值不足)

a = 1, 10, 100, 1000
# i, j, k = a             # ValueError: too many values to unpack (expected 3)
# i, j, k, l, m, n = a    # ValueError: not enough values to unpack (expected 6, got 4)

针对变量个数少于元素个数的情况,可采用星号表达式解决。借助星号表达式,可使一个变量接收多个值。需注意两点:其一,经星号表达式修饰的变量会转变为一个列表,该列表可能包含 0 个或多个元素;其二,在解包语法中,星号表达式仅能出现一次。

a = 1, 10, 100, 1000
i, j, *k = a
print(i, j, k)        # 1 10 [100, 1000]
i, *j, k = a
print(i, j, k)        # 1 [10, 100] 1000
*i, j, k = a
print(i, j, k)        # [1, 10] 100 1000
*i, j = a
print(i, j)           # [1, 10, 100] 1000
i, *j = a
print(i, j)           # 1 [10, 100, 1000]
i, j, k, *l = a
print(i, j, k, l)     # 1 10 100 [1000]
i, j, k, l, *m = a
print(i, j, k, l, m)  # 1 10 100 1000 []

补充一下,解包语法对所有的序列都成立,这就表示列表、range函数构造的范围序列甚至字符串都可以使用解包语法

a, b, *c = range(1, 10)
print(a, b, c) # 输出:1 2 [3,4,5,6,7,8,9]
a, b, c = [1, 10, 100]
print(a, b, c) # 输出:1 10 100
a, *b, c = 'hello'
print(a, b, c) # 输出:h ['e','l','l'] o

交换变量的值

交换变量的值是写代码时经常用到的一个操作,但是通常交换两个变量的值都需要借助一个中间变量才能做到,如果不用中间变量就需要使用比较晦涩的位运算来实现。在 Python 中,交换两个变量ab的值只需要使用如下所示的代码。

a, b = b, a

同理,如果要将三个变量abc的值互换,即b的值赋给ac的值赋给ba的值赋给c,也可以如法炮制。

a, b, c = b, c, a

上面的操作并没有用到打包和解包语法,Python 的字节码指令中有ROT_TWOROT_THREE这样的指令可以直接实现这个操作,效率是非常高的。但是如果有多于三个变量的值要依次互换,这个时候是没有直接可用的字节码指令的,需要通过打包解包的方式来完成变量之间值的交换。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

web Rookie

此处应有打赏,就看兄弟你的啦.

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值