全面深入了解python(三)

全面深入了解python(三)

1. 切片

在python里,列表、元组和字符串这类序列类型都支持切片操作。

1.1 为什么切片和区间会忽略最后一个元素

在切片和区间不包含最后一个元素是python的风格,这个习惯符合python、c和其他语言里以0作为起始下标的传统。

  • 当只有最后一个位置信息时,可以快速看出切片和区间里有几个元素:range(3)和my_list[:3]都返回3个元素。
  • 当起止位置信息都可见时,用后一个数减去第一个下标(stop-start)可快速计算出切片长度。
  • 可以用任意一个下标把序列分割成不重叠的两部分,my_list[:x]和my_list[x:]即可。
>>> l = [10,20,30,40,50,60]
>>> l[:2]
[10, 20]
>>> l[2:]
[30, 40, 50, 60]
1.2 对对象进行切片

我们可以用s[a:b:c]的形式对s在a和b之间以c为间隔取值,c的值可以为负,负值意味着反向取值。

>>> s = 'computer'
>>> s[::3]
'cpe'
>>> s[::-1]
'retupmoc'
>>> s[::-2]
'rtpo'

如果还记得(一)中的例子,就会对order_card[11::13]有印象,从k开始(即下标11),间隔13取值,这样就把相同大小不同花色的四张牌全部取出来。

>>> order_card[11::13]#前面是索引,后面是步长
[Card(rank='K', suit='spades'), Card(rank='K', suit='diamonds️'), Card(rank='K', suit='clubs️'), Card(rank='K', suit='hearts️')]

a:b:c这种用法只能作为索引或者下标用在[]中来返回一个切片对象:slice(a,b,c)

#下面第一行标数字是为了方便取下标
>>> market = """
... 0     6                             35               50   53         
... 1752  Iphone xs max                   12800             5   64000
... 1108  Huawei Mate20 pro               6400              3   19200
... 2091  Xiaomi Mi9                      3500              7   24500
... 1832  OnePlus 6T                      3400              2   6800
... """
>>> SKU = slice(0,6)
>>> name = slice(6,35)
>>> price = slice(35,50)
>>> quantity = slice(50,53)
>>> total = slice(53,None)
#以换行符分割,列表前2个是空字符串和辅助字符串`0 6 35 50 53`,所以下标从2开始
>>> line_items = market.split('\n')[2:]
>>> for item in line_items:
...     print(item[price],item[name])
... 
   12800        Iphone xs max                
   6400         Huawei Mate20 pro            
   3500         Xiaomi Mi9                   
   3400         OnePlus 6T  

如果你接触过python的外部库numpy,应该就有一定的印象。[]运算符里还可以使用以逗号分开的多个索引或切片,二维的numpy.ndarray就可以用a[i,j]这种形式获取,或者a[m:n,p:q]的方式获取二维切片。

1.3 给切片赋值

如果把切片放在赋值语句的左边,或者作为del操作的对象,我们就可以对序列进行嫁接、切除或修改操作。

>>> q = list(range(10))
>>> q
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
#可以进行嫁接
>>> q[2:5] = [20,30]
>>> q
[0, 1, 20, 30, 5, 6, 7, 8, 9]
#可以进行切除
>>> del q[5:7]
>>> q
[0, 1, 20, 30, 5, 8, 9]
#按步长进行等量修改
>>> q[3::2] = [11,22]
>>> q
[0, 1, 20, 11, 5, 22, 9]
#右边必须是可迭代对象
>>> q[2:5] = 100
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: can only assign an iterable
>>> q[2:5] = [100]
>>> q
[0, 1, 100, 22, 9]

2. list.sort方法和内置函数sorted

list.sort方法会就地排序列表,不会把原列表重新复制一遍,这是这个方法返回值是None的原因。其实返回None其实是Python的一个惯例:如果一个函数或者方法对对象进行的是就地改动,那它就应该返回None,好让调用者知道传入的参数发生了变动而且没产生新的对象。

内置函数sorted正好和list.sort相反,它会新建一个列表作为返回值,可以接受任何形式的可迭代对象作为参数,甚至包括不可变序列或生成器。不管sorted接受的是怎样的参数,它最后都会返回一个列表。

reverse和key是list.sort方法和内置函数sorted都具有的可选参数。

reverse:如果被设定为True,被排序的序列里的元素会以降序输出,默认值是False。

Key:一个只有一个参数的函数,这个函数会被用在序列里的每个元素上,所产生的结果是排序算法依赖的对比关键字。参数默认值是恒等函数,以元素自己来排序。

>>> phones = ['huawei','iphone','xiaomi','honor','oneplus']
#内置函数排序
>>> sorted(phones)
['honor', 'huawei', 'iphone', 'oneplus', 'xiaomi']
>>> phones
['huawei', 'iphone', 'xiaomi', 'honor', 'oneplus']
#降序排序
>>> sorted(phones,reverse=True)
['xiaomi', 'oneplus', 'iphone', 'huawei', 'honor']
#以长度排序
>>> sorted(phones,key=len)
['honor', 'huawei', 'iphone', 'xiaomi', 'oneplus']
#降序以长度排序
>>> sorted(phones,key=len,reverse=True)
['oneplus', 'huawei', 'iphone', 'xiaomi', 'honor']
>>> phones
['huawei', 'iphone', 'xiaomi', 'honor', 'oneplus']
#对原列表就地排序,返回值None会被控制它忽略
>>> phones.sort()
#本身被排序
>>> phones
['honor', 'huawei', 'iphone', 'oneplus', 'xiaomi']
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值