Python的序列切片
生活随笔
收集整理的這篇文章主要介紹了
Python的序列切片
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
? ? ? ?Python提供了一種把序列切成小塊的操作,稱為切片(slice)操作,其本質是訪問由序列中的某些元素所構成的子集。Python的序列數據結構都支持切片操作,如列表、元組、字符串等,切片操作可以說是日常應用中最常使用的Python特性之一。(1)基本寫法sequence[start : end]sequence:表示序列,可以是列表、字符串、元組等;start:起始索引;end:結束索引。a = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
b = a[0:5]
c = a[:]
d = a[5:15]
print('a=', a, 'b=', b, 'c=', c, 'd=', d)輸出結果:a=?[1,?2,?3,?4,?5,?6,?7,?8,?9,?10]b=?[1,?2,?3,?4,?5]c=?[1,?2,?3,?4,?5,?6,?7,?8,?9,?10]d=?[6,?7,?8,?9,?10]可以看出:? ? ? ?1)序列a沒有變化,說明切片(slice)操作不改變原序列,而是生成一個新序列;? ? ? ?2)序列b的結果說明從頭切片的話,索引值是從0開始的,另外start所指元素在切片結果內,而end所指元素則不包括在切片結果中,說明切片[start:end]是一個半閉區間;? ? ? ?3)序列c結果說明從頭切片的話,start索引值0可以省略,如果取到序列末尾,end也應該省略,這樣更清爽;? ? ? ?4)序列d結果說明索引范圍不能越過序列本身邊界,越過邊界自動取邊界值(Python3特性,在Python2會報錯)。(2)負值索引
? ? ? ?若要從序列尾部向前算,則可以用負值表示相關偏移量。a = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
b = a[:-1]
c = a[-3:]
print('b=', b, 'c=', c)輸出結果:b=?[1,?2,?3,?4,?5,?6,?7,?8,?9]c=?[8,?9,?10]可以看出:? ? ? ?1)序列b比a少了最后一個元素,說明:-1表示最后一個元素;? ? ? ?2)序列c結果表明:用-n代表倒數第n個元素,并且即使start索引是負數,切片順序也是從前往后的。(3)反向和步進操作
? ? ? ?除了基本寫法外,Python還提供了sequence[start : end : stride]的寫法,以實現步進式切割。看示例:s = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
a = s[::2]
b = s[::-1]
c = s[::-2]
print('a=', a, 'b=', b, 'c=', c)輸出結果:a=?[1,?3,?5,?7,?9]b=?[10,?9,?8,?7,?6,?5,?4,?3,?2,?1]c=?[10,?8,?6,?4,?2]? ? ??可以看出:? ? ? ?1)序列a為序列s每隔2個元素進行取值,說明有stride的話按步進值間隔取序列中的元素;? ? ? ?2)序列b與序列s為反向,說明步進值為負值的話,實施的是反向操作,從序列末尾從后往前取元素。? ? ? ?3)序列c的結果說明使用負數布進值,除了按照反向操作外,也按照數字大小間隔取元素。
一般的應用情況下,與正向切片相比,反向切片和步進操作使用相對較少,但需要用的話,是非常好用且異常簡潔的。看一個反向操作的經典應用:回文字符串判斷,回文字符串是指aba、abba、cccbccc、aaaa這種左右對稱的字符串。先看C語言的經典實現:bool fun(char str[])
{
int i, j, n;
n = strlen(str);
for (i = 0, j = n-1; i <= (n-1)/2; i++, j--)
{
if (str[i] != str[j])
break;
}
if i > j
return True;
else
return False;
}
再看Python中利用反向切片操作的實現,異常簡潔:def fun(str):
return str == str[::-1](4)不要同時指定start,end和stride? ? ? ?按照《Effective Python》一書中的說法,切片操作既有start和end,又有stride的話,可能會令人費解,犧牲了可讀性,尤其是有負值索引和負的步進值情況下。看示例:s = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
a = s[-2:2:-2]
print(a)
輸出結果:a=?[9,?7,?5]? ? ? ?上例意思是從序列s倒著數第二個元素(包含)到序列s正著數第二個元素(不包含)之間的范圍(注意切片操作范圍是半閉區間)按步進值2進行反向切片,確實有點繞口,但也還算好懂。
? ? ? ?改進方式可以考慮使用兩條賦值語句代替,具體方法可是先做范圍切片,再做步進切片,也可以先做步進切片,再做范圍切片。個人認為先范圍再步進的方法更好。
s = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
a = s[-2:2:-2]
b = s[3:len(s)-1]
c = b[::-2]
print('a=', a, 'c=', c)輸出結果:a=?[9,?7,?5]c=?[9,?7,?5]? ? ? ?上例中b和c先對s做范圍切割,再做步進切割。? ? ? ?實際工作中如果思路清晰,切片使用熟練,同時指定start,end和stride也無不妥,畢竟就3個參數而已。
b = a[0:5]
c = a[:]
d = a[5:15]
print('a=', a, 'b=', b, 'c=', c, 'd=', d)輸出結果:a=?[1,?2,?3,?4,?5,?6,?7,?8,?9,?10]b=?[1,?2,?3,?4,?5]c=?[1,?2,?3,?4,?5,?6,?7,?8,?9,?10]d=?[6,?7,?8,?9,?10]可以看出:? ? ? ?1)序列a沒有變化,說明切片(slice)操作不改變原序列,而是生成一個新序列;? ? ? ?2)序列b的結果說明從頭切片的話,索引值是從0開始的,另外start所指元素在切片結果內,而end所指元素則不包括在切片結果中,說明切片[start:end]是一個半閉區間;? ? ? ?3)序列c結果說明從頭切片的話,start索引值0可以省略,如果取到序列末尾,end也應該省略,這樣更清爽;? ? ? ?4)序列d結果說明索引范圍不能越過序列本身邊界,越過邊界自動取邊界值(Python3特性,在Python2會報錯)。(2)負值索引
? ? ? ?若要從序列尾部向前算,則可以用負值表示相關偏移量。a = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
b = a[:-1]
c = a[-3:]
print('b=', b, 'c=', c)輸出結果:b=?[1,?2,?3,?4,?5,?6,?7,?8,?9]c=?[8,?9,?10]可以看出:? ? ? ?1)序列b比a少了最后一個元素,說明:-1表示最后一個元素;? ? ? ?2)序列c結果表明:用-n代表倒數第n個元素,并且即使start索引是負數,切片順序也是從前往后的。(3)反向和步進操作
? ? ? ?除了基本寫法外,Python還提供了sequence[start : end : stride]的寫法,以實現步進式切割。看示例:s = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
a = s[::2]
b = s[::-1]
c = s[::-2]
print('a=', a, 'b=', b, 'c=', c)輸出結果:a=?[1,?3,?5,?7,?9]b=?[10,?9,?8,?7,?6,?5,?4,?3,?2,?1]c=?[10,?8,?6,?4,?2]? ? ??可以看出:? ? ? ?1)序列a為序列s每隔2個元素進行取值,說明有stride的話按步進值間隔取序列中的元素;? ? ? ?2)序列b與序列s為反向,說明步進值為負值的話,實施的是反向操作,從序列末尾從后往前取元素。? ? ? ?3)序列c的結果說明使用負數布進值,除了按照反向操作外,也按照數字大小間隔取元素。
一般的應用情況下,與正向切片相比,反向切片和步進操作使用相對較少,但需要用的話,是非常好用且異常簡潔的。看一個反向操作的經典應用:回文字符串判斷,回文字符串是指aba、abba、cccbccc、aaaa這種左右對稱的字符串。先看C語言的經典實現:bool fun(char str[])
{
int i, j, n;
n = strlen(str);
for (i = 0, j = n-1; i <= (n-1)/2; i++, j--)
{
if (str[i] != str[j])
break;
}
if i > j
return True;
else
return False;
}
再看Python中利用反向切片操作的實現,異常簡潔:def fun(str):
return str == str[::-1](4)不要同時指定start,end和stride? ? ? ?按照《Effective Python》一書中的說法,切片操作既有start和end,又有stride的話,可能會令人費解,犧牲了可讀性,尤其是有負值索引和負的步進值情況下。看示例:s = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
a = s[-2:2:-2]
print(a)
輸出結果:a=?[9,?7,?5]? ? ? ?上例意思是從序列s倒著數第二個元素(包含)到序列s正著數第二個元素(不包含)之間的范圍(注意切片操作范圍是半閉區間)按步進值2進行反向切片,確實有點繞口,但也還算好懂。
? ? ? ?改進方式可以考慮使用兩條賦值語句代替,具體方法可是先做范圍切片,再做步進切片,也可以先做步進切片,再做范圍切片。個人認為先范圍再步進的方法更好。
s = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
a = s[-2:2:-2]
b = s[3:len(s)-1]
c = b[::-2]
print('a=', a, 'c=', c)輸出結果:a=?[9,?7,?5]c=?[9,?7,?5]? ? ? ?上例中b和c先對s做范圍切割,再做步進切割。? ? ? ?實際工作中如果思路清晰,切片使用熟練,同時指定start,end和stride也無不妥,畢竟就3個參數而已。
總結
以上是生活随笔為你收集整理的Python的序列切片的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Python的列表推导式
- 下一篇: Python的zip