python 3.x较之较早的版本是一次较大的升级,为了不带入更多累赘,python 3.x没有向下兼容。所以大部分早期python版本的程序都无法再python 3.x上执行。
print输出的应用
print语句:print “内容” 变成 print(“内容”)函数。
如:
python 2.7
>>>print "python", "cookbook"
python cookbook
python 3.5.3
>>>print("python", "cookbook")
python cookbook
但是python2.6之后可以通过以下方法使用print()函数:
如果直接使用
>>>print("python", "cookbook")
('python', 'cookbook')
需要导入__future__ 包里面的print_function:
>>>from __future__ import print_function
>>>print("python", "cookbook", sep=' ')
python cookbook
unicode
python 2.x 有ASCII()类型, unicode()是单独的,不是byte类型。而python 3.x 终于有了unicode(utf-8)字符串,以及一个字节类:byte和bytearrays。
python2.x以下用法会报错:
>>>string = '中国'
>>>print string
SyntaxError: Non-ASCII character '\xe4'
而由于python3.x源码文件中默认使用utf-8编码,这就使python3.x不会报错。
另外还发现一个有趣的事,可以 用中文来命名变量,但是极度不建议这么做:
>>>中国 = '各个国家有各个国家的国歌'
>>>print(中国)
各个国家有各个国家的国歌
除法运算
python的除法有两个运算符,/和//。
在python 2.x中除法就跟我们熟悉的大多数语言差不多,整数相除的结果是一个整数,把小数部分完全忽略掉,浮点数除法会保留小数点的部分得到一个浮点数的结果。
在python 3.x中/除法不再这么做了,对于整数之间的相除,结果也会是浮点数。
Python 2.x:
>>> 1 / 2
0
>>> 1.0 / 2.0
0.5
Python 3.x:
>>> 1/2
0.5
而对于//除法,这种除法叫做floor除法,会对除法的结果自动进行一个floor操作,也就是向下取整的意思,取不大于该数的整数。在python 2.x和python 3.x中是一致的。
python 2.x:
>>> -3 // 2
-2
python 3.x:
>>> -3 // 2
-2
注意的是并不是舍弃小数部分,而是执行 floor 操作。
如果要只截取整数部分,那么需要使用 math 模块的 trunc 函数,
python 3.x:
>>> import math
>>> math.trunc(3 / 2)
1
>>> math.trunc(-3 / 2)
-1
异常处理
在Python 3.x 中使用as作为关键词。捕获异常的方法由except exc, var改为except exc as var。
使用except(exc, exc2) as var 可以同时捕获多种异常。python2.6已经支持这两种语法。
1、在使用2.x时,所有类型的对象都可以被直接抛出;在使用3.x时,只有继承BaseException的对象才可以被抛出。
2、2.x raise语句使用逗号将抛出对象类型和参数分开,3.x取消了这种写法,直接调用构造函数抛出对象即可。
在2.x时代,异常在代码中除了表示程序错误,还经常做一些普通控制结构应该做的事情,在3.x中可以看出,设计者让异常变的更加专一,只有在错误发生的情况才能去用异常捕获语句来处理。
xrange
在python2中xrange()创建迭代对象的方法非常常用。例如for循环或者列表、字典、集合的推导式。这个方法就类似于一个生成器。但是这个 xrange-iterable 是无穷的,意味着你可以无限遍历。
由于它的惰性求值,如果你不得仅仅不遍历它一次,xrange() 函数 比 range() 更快(比如 for 循环)。尽管如此,对比迭代一次,不建议你重复迭代多次,因为生成器每次都从头开始。
在 Python 3 中,range() 是像 xrange() 那样实现以至于一个专门的 xrange() 函数都不再存在(在 Python 3 中 xrange() 会抛出命名异常)。
python 2.x
>>>for i in xrange(1, 3):
... print i
1
2
>>>for i in range(1, 3):
... print i
1
2
python 3.x
>>> for i in xrange(1,3):
... print(i)
...
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
NameError: name 'xrange' is not defined
>>> for i in range(1,3):
... print(i)
...
1
2
再看用python2.x实现的两个函数的数据类型:
>>> x = xrange(1,3)
>>> print type(x)
<type 'xrange'>
>>> x = range(1,3)
>>> print type(x)
<type 'list'>
其中xrange()实现的是一个生成器,range()实现的是一个list。
import time
num = 0
tem = 0
time1 = time.time()
for i in range(1, 10000000):
num += 3*i
time2 = time.time()
for i in xrange(1, 10000000):
tem += 3*i
time3 = time.time()
print time2-time1, time3-time2
输出:14.8169999123 12.7739999294
可见xrange的性能较优。
在python 3.x 中将xrange取消了,并且range的类型也改变了,变成了range类型,也是一个生成器。
>>> x = range(1,3)
>>> print(type(x))
<class 'range'>
python 3.x测试range()函数:
import time
sums = 0
x1 = time.clock()
for i in range(1, 100000000):
sums += 3*i
x2 = time.clock()
print(x2-x1)
输出:12.335192955545493
重新测了三次,python3.x的range()与python 2.x版本的xrange()的性能差距不大。
八进制字面量表示
python 3.x里面八进制数必须写成0o100,原先python2.x里面的0100不能用了,如下面例子:
python 2.x
>>> print 0o100, 0b100, 0x100, 0100
64 4 256 64
python 3.x
>>>print(0o100, 0b100, 0x100, 0100)
print(0o100, 0b100, 0x100, 0100)
^
SyntaxError: invalid token
不等运算符
Python 2.x中不等于有两种写法 != 和 <>
Python 3.x中去掉了<>, 只有!=一种写法。
多个模块被改名(根据PEP8)
旧的名字 | 新的名字 |
---|---|
_winreg | winreg |
ConfigParser | configparser |
copy_reg | copyreg |
Queue | queue |
SocketServer | socketserver |
repr | reprlib |
StringIO模块现在被合并到新的io模组内。 new, md5, gopherlib等模块被删除。 Python 2.6已经支援新的io模组。
httplib, BaseHTTPServer, CGIHTTPServer, SimpleHTTPServer, Cookie, cookielib被合并到http包内。
取消了exec语句,只剩下exec()函数。 Python 2.6已经支援exec()函数。
数据类型
1)Py3.X去除了long类型,现在只有一种整型——int,但它的行为就像2.X版本的long
2)新增了bytes类型,对应于2.X版本的八位串,定义一个bytes字面量的方法如下:
>>> b = b'china'
>>> type(b)
<type 'bytes'>
str对象和bytes对象可以使用.encode() (str -> bytes) or .decode() (bytes -> str)方法相互转化。
>>> s = b.decode()
>>> s
'china'
>>> b1 = s.encode()
>>> b1
b'china'
3)dict的.keys()、.items() 和.values()方法返回迭代器,而之前的iterkeys()等函数都被废弃。同时去掉的还有 dict.has_key(),用 in替代它吧 。
键盘输入
在python2.x中raw_input()和input( ),两个函数都存在,其中区别为:
raw_input()—将所有输入作为字符串看待,返回字符串类型。
input()-----只能接收"数字"的输入,在对待纯数字输入时具有自己的特性,它返回所输入的数字的类型(int, float )。
在python3.x中raw_input()和input( )进行了整合,去除了raw_input(),仅保留了input()函数,其接收任意任性输入,将所有输入默认为字符串处理,并返回字符串类型。
map、filter 和 reduce的使用
这三个函数号称是函数式编程的代表。在 Python3.x 和 Python2.x 中也有了很大的差异。
首先在 Python2.x 的交互下输入 map 和 filter,看到它们两者的类型是 built-in function(内置函数):
>>> map
<built-in function map>
>>> filter
<built-in function filter>
>>>
它们输出的结果类型都是列表:
>>> map(lambda x:x *2, [1,2,3])
[2, 4, 6]
>>> filter(lambda x:x %2 ==0,range(10))
[0, 2, 4, 6, 8]
>>>
但是在Python 3.x中的例子如下:
>>> map
<class 'map'>
>>> map(print,[1,2,3])
<map object at 0x10d8bd400>
>>> filter
<class 'filter'>
>>> filter(lambda x:x % 2 == 0, range(10))
<filter object at 0x10d8bd3c8>
首先它们从函数变成了类,其次,它们的返回结果也从当初的列表成了一个可迭代的对象, 我们尝试用 next 函数来进行手动迭代:
>>> f =filter(lambda x:x %2 ==0, range(10))
>>> next(f)
0
>>> next(f)
2
>>> next(f)
4
>>> next(f)
6
对于比较高端的 reduce 函数,它在 Python 3.x 中已经不属于 built-in 了,被挪到 functools 模块当中。