Python基础笔记

No.1

python交互界面(解释器)提示符

Python的交互界面有两种提示符,分别是主提示符“>>>”和次提示符“...”。
  主提示符是解释器告诉你它在等待你输入下一个语句。
  次提示符是告诉你解释器正在等待你输入当前语句的其他部分。

No.2

python交互界面(解释器)中print语句和只输入变量名显示值的区别

print语句调用str()函数显示对象。
  只输入变量名则调用repr()函数显示对象。

No.3

下划线(_)在解释器中表示最后一个表达式的值。

>>> a=1
>>> b=2
>>> a
1
>>> b
2
>>> _
2
>>>

No.4

%号可以实现字符串替换功能。

%s表示由一个字符串来替换

>>> name='Mason'
>>> print 'My name is %s'%name
My name is Mason

%d表示由一个整型来替换

>>> old=40
>>> print "I'm %d years old"%old
I'm 40 years old

%f表示由一个浮点型来替换

>>> number=25.4
>>> print 'The number is %f'%number
The number is 25.400000

有多个替换时可以将替换的值放在元组中。

>>> a='abc'
>>> b='def'
>>> c=25
>>> print '示例:%s%s%d'%(a,b,c)
示例:abcdef25

用来替换的量还可以是一个表达式。

>>> a='abc'
>>> b='def'
>>> print '示例:%s'%(a+b)
示例:abcdef

No.5

“>>”用来实现输出重定向(Python2)
>>> with open(r'c:\temp\a.txt','w') as file:
...     print >>file,'Fatal error: invalid input'
...
c:\temp\a.txt

No.6

尽量在函数外做用户交互操作(输入/输出)

函数应该保持其清晰性,也就是它只应该接受参数,返回结果。而不在函数内部使用print和raw_input()/input()函数。
  特例是如果函数的基本功能就是为了得到用户输入,或者是为了输出信息,这时在函数内使用print和raw_input()/input()函数也未尝不可。

No.7

注释
  • #号     从#开始,到行末都是注释,可以在一行的任何地方开始,解释器会忽略掉该行#之后的所有内容。
  • 文档字符串  可以在模块、类或者函数的起始添加一个字符串,起到在线文档的功能,可以使用help()函数调用,也可以使用“对象名称.__doc__”访问。
>>> def foo():
...     "This is a doc string."
...     return True
...
>>> print foo()
True
>>> help(foo)
Help on function foo in module __main__:
    
foo()
    This is a doc string.
  
In [7]: print foo.__doc__
This is a doc string.

No.8

除法操作符(运算符)

除法操作符有两个,分别是“/”和“//”。

  • /  做传统除法
    传统除法:在Python2中,如果两个操作数都是整型的话,它将执行的是地板除,返回一个整型(Python2版本)。如果操作数之一是浮点型,则执行真正的除法。
      “/”在Python2和Python3中略有区别,在Python3中不管两个操作数是整形还是浮点型,“/”都是执行真正的除法。
#Python2示例
>>> 5/2
2
>>> 5.0/2
2.5
>>> 5//2
2
>>> 5.0//2
2.0

如果希望Python2在除法方面的行为与Python3一致,通过执行from __future__ import division可以实现。

>>> from __future__ import division
>>> 5/2
2.5

备注future模块可以让Python2.7支持一些Python3的新特性。

地板除:不管操作数为何种数值类型,总是舍去小数部分,返回数字序列中比真正的商小的最接近(最大)的整数。

>>> -5//2
-3
>>> 5//2
2
  • //  总是做地板除
>>> 5//2
2
>>> 5.0//2
2.0
>>>-1//2
-1

No.9

在使用操作符进行运行时应合理使用括号增加代码的可读性。

No.10

变量命名

变量名由数字、字母和下划线组成。
  变量名只能以字母或下划线开头。
  变量名对大小写敏感,即ABC和aBC不是同一个变量。

No.11

布尔值

正常的表示方法是True、False,但实际上在做逻辑运算时,python把值为0或为空的对象(空列表、空元组、空字典等)以及None对象都当成False处理,除此以外的值都当成True处理。
  而在做数学运算时,python会把True当成整数1,而把False当成整数0.

>>> print True+5
6
>>> print False+5
5
>>> if 1:
...     print 'ok'
...
ok
>>> if 0:
...     print 'ok'
...
>>>

虽然python在逻辑运算时把None也当成Fasle处理,当在数据运算时,None不可以象False一样当成0处理,否则会报错。

>>> print None+5
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: unsupported operand type(s) for +: 'NoneType' and 'int'

布尔运算时当成False处理的值或对象如下:

  • None
  • False
  • 所有值为零的数
  • ""(空字符串)
  • [](空列表)
  • {}(空字典)
  • ()(空元组)
    除以上列出的值以外的对象的布尔值都是True.

No.12

python的五种内建数字类型
类型 工厂函数 示例
有符号整型 int() 101、84、-237、0x80、017、-680、-0X92
长整型 long() 29979062458L、-841401、0xDECADEDEADBEEEBADFEEDDEAL
布尔型 bool() True、False
浮点值 float() 3.14159、4.20E-10、-90.、6.055e23、-1.609E-19
复数型 complex() 6.23+1.5j、-1.23-875J、0+1J 9080665-8.31441J、 -.0224+0j

Python3中已经不再区分长整型和普通整型,普通整型就是长整型。同时取消了long()函数。

>>> 5654646546546544654654654646446566l
  File "<stdin>", line 1
    5654646546546544654654654646446566l
                                      ^
SyntaxError: invalid syntax
>>> 5654646546546544654654654646446566L
  File "<stdin>", line 1
    5654646546546544654654654646446566L
                                      ^
SyntaxError: invalid syntax
>>> 464658798754654654654444444444444444444444444444445656666666666666666666666666666666666666666666666666666
464658798754654654654444444444444444444444444444445656666666666666666666666666666666666666666666666666666

No.13【自本条开始部分示例会使用ipython解释器。“In [x](x是行号)”和“...:”分别是ipython的主提示符和次提示符。关于主提示符和次提示符参见No.1】

如果函数中没有return语句就会自动返回None对象。

No.14

在类实例化时显示类的名称

self.__class__.__name__

In [20]: class test(object):
    ...:     def __init__(self,nm='Jane Smith'):
    ...:         self.name=nm
    ...:     def show(self):
    ...:         print self.name
    ...:         print self.__class__.__name__
    ...:

In [21]: fool=test()

In [22]: fool.show()
Jane Smith
test

No.15

dir()函数

dir()函数显示对象的属性和方法,如果没有提供参数,则以列表的形式显示全局变量的名字。
显示全局变量的名字时区别于globals()函数,globals()函数是以字典的形式显示全局变量的名字和值。

No.16

访问对象(函数、模块等)的帮助(文档注释/文档字符串)  参见No.7注释
  • help()函数
In [9]: help(dir)
Help on built-in function dir in module __builtin__:
  
dir(...)
    dir([object]) -> list of strings

    If called without an argument, return the names in the current scope.
    Else, return an alphabetized list of names comprising (some of) the attributes
    of the given object, and of attributes reachable from it.
    If the object supplies a method named __dir__, it will be used; otherwise
    the default dir() logic is used and returns:
      for a module object: the module's attributes.
      for a class object:  its attributes, and recursively the attributes
        of its bases.
      for any other object: its attributes, its class's attributes, and
        recursively the attributes of its class's base classes.
  • “对象名称.__doc__”
In [10]: print dir.__doc__
dir([object]) -> list of strings
  
If called without an argument, return the names in the current scope.
Else, return an alphabetized list of names comprising (some of) the attributes
of the given object, and of attributes reachable from it.
If the object supplies a method named __dir__, it will be used; otherwise
the default dir() logic is used and returns:
  for a module object: the module's attributes.
  for a class object:  its attributes, and recursively the attributes
    of its bases.
  for any other object: its attributes, its class's attributes, and
    recursively the attributes of its class's base classes.

No.17

一行语句分多行书写

分三种情况:

  • \  在行末输入“\”,然后加车另起一行
In [1]: if (a==1) and \
   ...:      (b==0):
   ...:       print 'yes'
   ...:
  • 使用闭合操作符(小括号、中括号、花括号)时。
    单一语句在使用闭合操作符时,单一语句可以跨多行。
In [2]: print (4+
   ...:        6)
10
  • 三引号包括下的字符串也可以跨行书写。
 print '''Hello
   ...: World'''
Hello
World

使用三引号的字符串会保留原有的换行格式。

No.18

到底是选择空格还是选择制表符(Tab)来进行代码缩进?

使用空格或制表符这两种风格都是得到了Python的创始人的支持的,但制表符在不同的编辑器中的空白宽度不一样,所以建议还是使用4个空格来实现代码缩进。

No.19

同一行写多个语句

多个语句之间用“;”分号分隔即可。
  同一行上书写多条语句会降低代码的可读性,所以并不提倡。

In [6]: print 1;print 2;print 3
1
2
3

No.20

交换两个变量的值
In [1]: x=1

In [2]: y=2

In [3]: x,y=y,x

In [4]: x
Out[4]: 2

In [5]: y
Out[5]: 1

No.21

Python的内建(内置)对象(函数、类等)

Python的内建对象,包括函数、类等(比如print、str、list、help等等)是“__builtins__”模块的成员,Python在启动时自动导入,不需要用户使用import手工导入。可以使用dir(\_\_builtins__)查看__builtins__模块中包括哪些属性和方法。

No.22

下划线在给对象或变量命名时的特殊含义
  • _xxx  私有的,使用from module import *导入时忽略
  • _xxx_  系统定义的名子,保留
      建议程序员避免用下划线做为变量名或对象名的开始,除非明确知道定义的是私有变量。

No.23

import this

无论是在程序里还是在解释器中输入import this都会显示一个叫“python之禅”的东西。是python编写程序应有的风格概括,很有名。

In [36]: import this
The Zen of Python, by Tim Peters

Beautiful is better than ugly.
Explicit is better than implicit.
Simple is better than complex.
Complex is better than complicated.
Flat is better than nested.
Sparse is better than dense.
Readability counts.
Special cases aren't special enough to break the rules.
Although practicality beats purity.
Errors should never pass silently.
Unless explicitly silenced.
In the face of ambiguity, refuse the temptation to guess.
There should be one-- and preferably only one --obvious way to do it.
Although that way may not be obvious at first unless you're Dutch.
Now is better than never.
Although never is often better than *right* now.
If the implementation is hard to explain, it's a bad idea.
If the implementation is easy to explain, it may be a good idea.
Namespaces are one honking great idea -- let's do more of those!

这儿有一篇《<Python之禅>的翻译和解释》

No.24

对于全局变量的查找,总是先查找本地变量,所以从好的编程风格角度来说,除非必须,否则就要尽量使用局部变量代替全局变量。这样可以使用代码易于维护并提高性能、节省内存。
  因为模块也是全局变量,而且对于模块的查找总是先查找模块,再在模块中查找相应的属性或方法,所以对模块中的属性或方法的访问最好也能转换为本地引用,如下示例:

>>>import os
>>>ls=os.linesep

No.25

关于“__name__”

参见我的另一篇文章:《关于“__name__”变量》

No.26

Python中的对象

Python使用对象模型来存储数据。构造任何类型的值都是一个对象。
  Python对象都拥有三个特性:身份,类型和值

  • 身份  对象的身份可以使用内建函数id()来得到,这个值可以被认为是该对象的内存地址。
>>> a='a'
>>> id(a)
57553696
  • 类型  可以使用内建函数type()查看python对象的类型。
>>> a='a'
>>> type(a)
<type 'str'>
>>>

在python中,对象的类型本身也是一个对象,所以使用type()函数返回的值也是一个对象,而不是一个普通的字符串。

>>> a='a'
>>> type(a)
<type 'str'>
>>> type(type(a))
<type 'type'>
  • 值   对象表示的数据。
>>> a='a'

变量a的值即是字符'a'.

No.27

None对象(或值)

None是Python中一个特别的对象,称之为Null对象。不支持运算(逻辑运算除外),也没有任何内建方法。当代表布尔值时,总是代表False(参见NO.11)。

NO.28

对象值比较运算

  • 比较运算时,多个比较运算可以在一行上进行。
>>>4>3==3
True
>>> 3<4<5
True
>>>4<3<5!=2<7
False
  • 比较运算符:
运算符 说明
< 小于
> 大于
<= 小于等于
>= 大于等于
== 等于
<>!= 不等于(说明,未来很可能不再支持“<>”,建议使用“!=”)

No.29

参见我的另一篇文章《Python对象的身份比较》

No.30

逻辑运算符的优先级
优先级顺序(从上往下依次为从高到低) 运算符 说明
1 not 逻辑非(取反)
2 and 逻辑与(并且)
3 or 逻辑或(或者)

NO.31

str()、repr()、\的区别

参见我的另一篇文章《Python中str()、repr()、\的区别》

NO.32

Python基本内建数据对象原始类型分类

“基本内建数据对象原始类型”这个拗口的名称照搬自《Python核心编程(第二版)》,不是很好懂,但这不妨碍对下面内容的理解。

  • 按能容纳一个值还是多个值来区分对象类型。
      一个能保存单个字面对象的类型,称之为原子或标量存储。
      可以容纳多个对象的类型,称之为容器存储(容器对象有时会被称为复合对象)。容器对象能够容纳不同类型的对象。
分类 Python类型
标量/原子类型 数值(所有的数值类型)、字符串(全部是文字)
容器类型 列表、元组、字典
  • 按对象创建成功后值是否可以进行更新分为可变类型和不可变类型。
分类 Python类型
可变类型 列表、字典
不可变类型 数字、字符串、元组
  • 按访问存储的数据的方式分为直接访问、序列、映射。
    直接访问:数值
>>> a=4
>>> a
4

序列访问:容器内的元素按从0开始的索引顺序排列,可以通过索引一次访问一个元素或多个元素。

>>> a=['a','b','c']
>>> a[1]
'b'

映射访问:容器内的元素无序存放,通过一个唯一的键来访问。

>>> a={'a':1,'b':2,'c':3}
>>> a['a']
1
分类 Python类型
直接访问 数字
序列访问 字符串、列表、元组
映射访问 字典

No.33

Python整型数字的八进制和十六进制表示

Python的整型数字支持直接表示为八进制和十六进制。
八进制整型数字以“0”开始。

>>> 025674
11196

十六进制整型数字以“0x”或“0X”开始。

>>> 0x25e33
155187

NO.34

Python中不同类型的数值运算中的类型转换

Python中的数值有多种类型、包括整型(普通整形、长整型)、布尔型(0和1)、浮点数、复数等。
  当不同类型的数值进行运算时,Python需要先将运算符两边的数值(操作数)转换为同一种类型,转换的具体的规则如下:

  • 如果有一个操作数是复数,另一个操作数被转换为复数;
    否则
  • 如果有一个操作数是浮点数,另一个操作数被转换为浮点数;
    否则
  • 如果有一个操作数是长整型,则另一个操作数被转换为长整型;
    否则
  • 两个操作数必然都是普通整型,无须类型转换。

一般来说以上的转换是在运算过程中由Python自动进行的,程序员无须自己编码处理类型转换。
  在Python2中有一个手工对数值类型时进行转换的函数coerce(),转换规则跟上面一样。这个函数在Python3中不再支持。

No.35

几个常用的数值运算及转换函数

  • abs()  返回参数的绝对值
>>> abs(5)
5
>>> abs(-5)
5
  • divmod()  返回由参数的商和余数组成的元组,相当于把地板除(参见NO.8)和取余运算结合起来。
>>> divmod(5,2)
(2, 1)
>>> divmod(5.5,3)
(1.0, 2.5)
  • pow()
      这个函数可以接受三个参数,第三个参数可选。
      当只有两个参数时,pow()对两个参数进行指数计算,此时pow()函数的功能跟**运算符是一样的。
>>> pow(2,3)
8
>>> 2**3
8
>>> pow(5,-3)
0.008
>>> 5**-3
0.008

当pow()有三个参数时,会先对前两个参数进行指数运算,运算的结果再与第三个参数进行求余运算。pow(5,3,4)相当于5**3%4,但性能上前者要比后者要好。
  在《Python核心编程(第二版)》中提到,这个先计算指数再求余的特性主要用于密码运算。

>>> pow(5,3,4)
1
>>> 5**3%4
1
  • round()
      此函数提供四舍五入运算(区别于传统的四舍五入,这个下面说)功能,可以有两个参数,第二个是小数位参数,可选。
      如果不提供小数位参数,该函数返回与第一个参数最接近的整型(Python3)或伪整型数值(Pyhton2,类似于5.0这样的表述)。
Python 2.7.13 (v2.7.13:a06454b1afa1, Dec 17 2016, 20:42:59) [MSC v.1500 32 bit (Intel)] on win32
Type "help", "copyright", "credits" or "license" for more information.
>>> round(5.3)               #Python2
5.0
Python 3.6.0 (v3.6.0:41df79263a11, Dec 23 2016, 07:18:10) [MSC v.1900 32 bit (Intel)] on win32
Type "help", "copyright", "credits" or "license" for more information.
>>> round(5.3)               #Python3
5

如果提供了小数位参数,则该参数告诉round()函数将结果精确到小数点后指定位数。

>>> round(5.12,1)
5.1

下面说一下为什么round()函数提供的四舍五入运算区别于传统的四舍五入。

>>> round(2.675,2)
2.67

上面的示例中可以看出使用round()函数对有一些数值进行四舍五入运算时得到的结果是不准确的。2.675这个数字四舍五入到小数点后2位应该是2.68,但round()函数运算的结果是2.67,这个与我们传统四舍五入运算的结果是不一样的。之所以出现这样的问题是因为使用2进制不能精确表示浮点数的原因,此处不做详细论述。所以大家在使用round()函数时要考虑到该因素。
  如果要得到精确的四舍五入运算结果可以参考math模块。

  • hex()、oct()
      这两个函数都是进制转换函数,分别将任意进制的整型对象(整数)分别转换为十六进制(hex())和八进制数(oct()字符串(注意,返回的对象是字符串,不是数值型对象)。
      关于十六进制和八进制的直接表达方式请参见No.33。
>>> hex(255)
'0xff'
>>> oct(255)
'0377'
>>> oct(0xff)
'0377'
>>> hex(0377)
'0xff'

再次强调一下,这两个函数的参数值只能是整型,而不能是实数。

  • chr()
      chr()函数接受0-255之间的一个整数(可以是十进制、八进制、十六进制以及长整型),将这个数转换成ASCII码表中对应的字符或字符串。
>>> chr(255)
'\xff'
>>> chr(65)
'A'
>>> chr(0255)
'\xad'
>>> 0255
173
>>> chr(173)
'\xad'
>>>
  • ord()
      ord()函数的任用跟chr()正好相反,该函数接受一个字符(注意不是字符串),将该字符转换成相应的ASCII码值。
>>> for x in 'abcdefg':
...     print ord(x)
...
97
98
99
100
101
102
103

NO.36

十进制数值

Python中的数值型在底层是用二进制表达的,而二进制数在一些情况下不能精确的表达浮点数(参见NO.35中的round()函数)。这对于要进行精确计算的人来说是很痛苦的,为此Python引入了十进制数这样的一个类型,通过导入内置模块decimal实现,该模块提供了以十进制方式对数值进行计算的支持。

>>> from decimal import Decimal
>>> d=Decimal('0.1')
>>> e=Decimal('1')
>>> d+e
Decimal('1.1')

也可以

>>> import decimal
>>> d=decimal.Decimal('0.1')
>>> e=decimal.Decimal('1')
>>> d+e
Decimal('1.1')

十进制数不可以跟普通的浮点型混用。

>>> from decimal import Decimal
>>> Decimal('0.1')+1.0
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: unsupported operand type(s) for +: 'Decimal' and 'float'

但是十进制数可以跟整型数值混用。

>>> from decimal import Decimal
>>> Decimal('0.1')+1
Decimal('1.1')

通过普通浮点型数值来创建十进制数会得到一个跟预想不一样的数字,事实上是先将普通浮点型转换为二进制数再转换为十进制数,这就触发了二进制数不能准确表达浮点型的问题。

>>> from decimal import Decimal
>>> Decimal(0.1)
Decimal('0.1000000000000000055511151231257827021181583404541015625')

所以如果要准确创建跟预想一样的十进制浮点数需要通过字符串来实现。

>>> from decimal import Decimal
>>> Decimal('0.1')
Decimal('0.1')

通过普通整型来创建十进制数,不存在上述问题。

>>> from decimal import Decimal
>>> Decimal(1)
Decimal('1')
>>> Decimal(5)
Decimal('5')

NO.37

序列

序列包括字符串、列表、元组。共同的特点是成员有序排列,可以通过下标偏移量访问,具有相同的访问和操作模式。

NO.38

序列运算符(操作符)
  • 连接运算符(+
      可以把两个相同的序列做连接。
>>> ['a','b','c']+[1,2,3]
['a', 'b', 'c', 1, 2, 3]
>>> a=['a','b','c']
>>> b=[1,2,3]
>>> a+b
['a', 'b', 'c', 1, 2, 3]

《Python核心编程》(第二版)中强调字符连接时使用+不如join()方法节约内存,速度也比不上。同样如果是列表合并+不如extend()方法节约内存且速度也比不上。

  • 重复操作符(*)
      将一个序列重复多次生成一个新的序列。
>>> ['a',2]*3
['a', 2, 'a', 2, 'a', 2]
>>> 'python'*3
'pythonpythonpython'
>>> ('a',1)*3
('a', 1, 'a', 1, 'a', 1)

注意,*号后面必须是一个整数,且不能超出短整型的范围。在Python3中已经取消了短整型和长整型的区别,整型就是长整型,但对于*号后面的数值仍旧有一定的范围要求,该数值如果过大仍旧会报错。具体的范围我没有求证。

>>> 'a'*1111111111111111111111111111111111111111111111111111111111111111111
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
OverflowError: cannot fit 'long' into an index-sized integer

如果*号后面的数值为负数会得到一个空序列。

>>> 'abc'*-1
''
>>> [1,2,3]*-2
[]
  • 切片运算符([]、[:])
      访问或获得序列中一个或部分连续元素的复制称之为切片。
[]  可以用方括号加一个下标的方式访问序列的每一个元素。
>>> a=[1,2,3,4]
>>> a[0]
1
>>> a[1]
2
>>> a[2]
3
>>> a[3]
4
>>> a[4]
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
IndexError: list index out of range

方括号中是序列的下标,或者称之为索引(index),索引值从0开始,len(序列)-1结束。也就是说如果有4个元素的一个序列,第一个元素的索引值为0,最后一个元素的索引值为3,如果索引值超出此范围则会报如上例中的错误。

索引值也可以是负值。

>>> a=[1,2,3,4]
>>> a[-1]
4
>>> a[-2]
3
>>> a[-3]
2
>>> a[-4]
1
>>> a[-5]
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
IndexError: list index out of range

当索引值为负值时,事实上是按照序列中元素排列序列的反方向来访问相应的元素。索引值为-1时代表最后一个元素,索引值为-2时代表倒数第二个元素,以此类推。所以当索引值为负值时,其范围为-1~-len(序列)。

[:]  可能通过在方括号中指定起始和结束的下标(索引值)来访问序列中的一组连续的元素。起始和结束下标用冒号分隔。
>>> a=[1,2,3,4]
>>> a[0:2]
[1, 2]
>>> a[1:3]
[2, 3]
>>> a[0:4]
[1, 2, 3, 4]
>>> a[1:4]
[2, 3, 4]
>>> a[0:-1]
[1, 2, 3]
>>> a[-4:-1]
[1, 2, 3]
>>> a='abcdefg'
>>> a[0:5]
'abcde'
>>> a[1:5]
'bcde'

注意,起始索引值是从0开始计算的,而不是从1开始计算的。所以设置起始索引值时,总是用元素的实际排列位置(从1开始计算的排列位置)减去1。[1,2,3,4]这样的列表,如果我要获取第2位到第3位共两个元素,那么起始位索引值应该是第2位减去1,即1。
  而结束索引值与起始索引值不一样,如果按照上面的规则索引值从0开始计算的话,结束索引值会比我们理解的索引值大1。同样是上面的例子,获取[1,2,3,4]列表中第2个和第3个元素的切片时,结束索引值为3。
  即[1,2,3,4][1:3]

>>> a=[1,2,3,4]
>>> a[1:3]
[2, 3]

这儿说的比较绕。总之要记住以下原则:
  1、索引值从0开始计算。
  2、对序列进行切片时,起始索引值是你要取的第一个元素实际排列位置减1,比如从第2个元素开始切片,则起始索引值为1,如果从第5个元素开始切片,则起始索引值为4。
  3、对序列进行切片时,结束索引值即是你要取的最后一个元素的实际排列位置(要取的最后一个元素的实际索引值<注意不是排列位置>加1),比如要从第2个元素取到第5个元素,则结束索引值即是5,即[2:5]。

当需要获得一个序列的完整切片(即复制一个序列)时可以使用以下方法。

In [1]: a=[1,2,3,4]

In [2]: a[0:4]
Out[2]: [1, 2, 3, 4]

In [3]: a[0:len(a)]
Out[3]: [1, 2, 3, 4]

In [4]: a[:]
Out[4]: [1, 2, 3, 4]

In [5]: a[None:None]
Out[5]: [1, 2, 3, 4]

需要强调的是:
  如果是要从序列的第一个元素开始切片,则第一个元素的索引可以省略,同样如果要切片到序列的最后一个元素,则最后一个元素的索引可以省略。所以上例中“In[4]”行中的a[:]即是省略了第一个元素和最后一个元素的索引的写法,同样可以实现从第一个元素切片到最后一个元素的目的。

当切片时,如果给出的最后一个元素的索引值超出序列的实际范围时并不会报错,参见下例。

>>> a=[1,2,3,4]
>>> a[0:100]
[1, 2, 3, 4]
  • 步长索引([::]
>>> a=[0,1,2,3,4]
>>> a[0:5:2]
[0, 2, 4]

从上例中可以看出,正常的切片操作中多了一个参数,之间用冒号分隔(不是逗号)。这第三个参数即为步长索引,类似于内建函数range()里面的步长参数。第1个冒号前后两个值仍旧是正常切片的索引值。所以上例也可以写成下面的样子。

>>> a=[0,1,2,3,4]
>>> a[::2]
[0, 2, 4]

步长索引设置为-1时,可以实现序列的逆序排列。

>>> a=[0,1,2,3,4]
>>> a[::-1]
[4, 3, 2, 1, 0]
>>> s='abcdefg'
>>> s[::-1]
'gfedcba'

当然步长索引也可以是其他负值,这样可以实现倒序的同时间隔切片。

>>> s='abcdefg'
>>> s[::-2]
'geca'

持续更新中...

参考资料

《Python核心编程》(第二版) 人民邮电出版社出版发行
《<Python之禅>的翻译和解释》 赖勇浩的编程私伙局(博客)

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 212,080评论 6 493
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,422评论 3 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 157,630评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,554评论 1 284
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,662评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 49,856评论 1 290
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,014评论 3 408
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,752评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,212评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,541评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,687评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,347评论 4 331
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,973评论 3 315
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,777评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,006评论 1 266
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,406评论 2 360
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,576评论 2 349

推荐阅读更多精彩内容

  • Zen of Python 参考:https://www.python.org/dev/peps/pep-0020...
    郭少悲阅读 322评论 0 1
  • Python环境配置及基础数据类型 写在最前:Python的厉害之处就不多说了,在机器学习的技能图谱中,Pytho...
    Hebborn_hb阅读 403评论 0 0
  • Python简介 Python历史 Python 是由 Guido van Rossum 在八十年代末和九十年代初...
    莫名其妙的一生阅读 1,044评论 0 2
  • 人生就像一条没有桥的河,活了十八年我才知道自己有多无能,曾经那个阳光的女孩去哪了呢。 为什么走错一步上天就再也不会...
    杜不懂的王明白阅读 179评论 0 0
  • “随礼”是中华古老民俗的延续,是一种亲朋好友之间感情的互动。由过去纯粹的真感情演变成现在的薄情寡义;由过去人生中的...
    雲淡风轻阅读 483评论 0 0