Python 2.5 的增进研究 ::-- ZoomQuiet [2006-11-10 02:46:55]
1. What's New in Python 2.5
1.1. O'Reilly
O'Reilly Emerging Telephony Conference 报道
ZoomQuiet 简译 ::-- ZoomQuiet [2006-11-10 03:16:37]
Contents
很难相信Python 已经有15年历史了,但是作为现代开发语言,Python 不断的在增进,这里只是简要的介绍全新的2.5 版本中的特性
向下兼容
- 尽管2.5 有很多变化,但是注意到很好的兼容己有的2.4 代码
条件语句
- 向C/C++学习,加入了条件语句的精简形式
以往
if x > 15: a = 1 else: a = 2
对比C 的3项式a = x > 15 ? 1 : 2;
现在Pt2.5 可以a = 1 if x > 15 else 2
当然出于Py 的魔力我们可以混合数据类型来使用,比如:
a = "abc" if x > 15 else 10
例外处理
- 有关例外处理,2.5进行了轻微的改进,更多的改进讨论中,计划在3.0 实现
在2.4.3 使用raise
>>> raise "Invalid argument" Traceback (most recent call last): File "<stdin>", line 1, in ? Invalid argument >>>
现在2.5
>>> raise "Invalid argument" __main__:1: DeprecationWarning: raising a string exception is deprecated Traceback (most recent call last): File "<stdin>", line 1, in <module> Invalid argument >>>
会多得一警报现在从 Exception 扩展了新类BaseException 并从中继承出了 KeyboardInterrupt 和 SystemExit 例外
- 随着例外处理的应用发展,现在的基本看法是:
- 例外信息应该是字串
- 传入参数应该是列表或是其它集成式的对象
更佳的例外捕获
try: test() except ZeroDivisionError: print "The expression resulted in a division-by-zero error" except Exception: print "Oops" else: print "All is good" finally: print "And everything is finished"
try语句进行了增进,可以混合使用更多的操作关键字
回传变量发生器
Generators 机制在 2.3 被加入,在2.5 有更多的地方进行了支持
例如: 一含有发生器 iterate 的类
1 class MyStuff: 2 def __init__(self): 3 self.a = [2,4,6,8,10,12] 4 def iterate(self): 5 i = 0 6 while i < len(self.a): 7 yield self.a[i] 8 i += 1
可以类似如此应用:
1 obj = MyStuff() 2 iterate = obj.iterate() 3 print iterate.next() 4 print iterate.next() 5 print iterate.next()
注意第2行从类实例返回一个iterate, 但是其本身没有从生成器获得参数,你需要使用 next() 来获取
在交互环境中可以观察到:
>>> print iterate <generator object at 0x009EB698> >>>
- 不同与C++ 使用反射机制来获取变量
这里使用 yield 构建了递归结构, 调用
iterate.next()
将进入函式段运行并返回self.a[i]
再次调用iterate.next() , 恢复上次运行结果的 i ,重新进入循环,直到再次到达 yield 处
注意,使用iterate = obj.iterate() ; 并没有立即调用实际函式,Python 瞧见有 yield结构,就创建一生成器对象来代替,你可以检验这一活动,通过加入print`
def iterate(self): print "Creating iterator" i = 0 ...rest of code...
这样,在iterate = obj.iterate()实例化时,你是看不到 Creating iterator 输出的,只有进行print iterate.next() 时,才会看到
这种编程支持,类似特性 Coroutine
使用 close()来指定结束;比如说,我们修订初始数组
def __init__(self): self.a = [2,4,6,8,10,12, None]
通过判别none来结束:
obj = MyStuff() iterate = obj.iterate() a = iterate.next() while a != None: print a a = iterate.next() iterate.close()
close()是2.5 中的新支持,如果你在iterate.close() 之后再调用'iterate.next()' 将获得一个StopIteration例外
这样的结构中,如何输入参数? 使用 sent()
1 class MyStuff2: 2 def __init__(self): 3 self.a = [2,4,6,8,10,12] 4 5 def iterate(self): 6 i = 0 7 while i < len(self.a): 8 val = yield self.a[i] 9 if val == None: 10 i += 1 11 else: 12 if val < 0: 13 val = 0 14 if val >= len(self.a): 15 val = len(self.a) -1 16 i = val
可以这样使用
>>> obj = gen1.MyStuff2() >>> i = iter(obj) >>> i.next() 2 >>> i.send(3) 8 >>> i.next() 10
注意,有内建函式iter() 支持自动识别,全权替代你自定的 iterator(),就象预设的 __iter__()
有点晕…………乱译了 上下文管理 基于提案PEP 843 增进了with功能
with open('/test.txt', 'r') as f: for line in f: process(line)
可以获得
>>> print f <closed file '/test.txt', mode 'r' at 0x009E6890>
輔助改进
__missing__(self, key) 可以来处理字典的关键字缺失
字串对象增加partition和rpartition函式
元组对象增加startswith和endswith函式
增强max和min
1 def myord(astr): 2 try: 3 num = int(astr) 4 return num 5 except: 6 return len(astr)
然后就可以使用进化版本的求最大
print max(['abc','100','a','xyz','1'], key=myord)
更多的内置函式,比如any()
>>> a = 10 >>> b = 20 >>> any([a>5, b>5]) True >>> any([a>50, b>50]) False >>> any([a>50, b>5]) True
类似的还有all()
详细可以参考其它语言方面的变化
库增进
专有库和DLL调用
>>> import ctypes >>> libc = ctypes.CDLL('c:/windows/system32/user32.dll') >>> print libc.GetDesktopWindow()
全面使用ElementTree处理XML
>>> from xml.etree import ElementTree as ET >>> tree = ET.parse('test.xml') >>> r = tree.getroot() >>> r <Element doc at aeeb70> >>> def trav(node, indent=0): ... for c in node.getchildren(): ... print ' '*indent, c.tag, ':', c.text ... trav(c, indent+1) ... >>> >>> trav(r) header1 : abc text1 : This is some b : text text1 : This is some more text >>>
SQLite支持增进
追加了sqlite3模块
import sqlite3 conn = sqlite3.connect('data.dat') c = conn.cursor() c.execute(''' create table members( id int, name varchar, login timestamp ) ''') c.execute(''' insert into members values (1,'jeff','2006-10-01') ''') c.execute(''' insert into members values (2,'angie','2006-10-02') ''') c.execute(''' insert into members values (3,'dylan','2006-10-03') ''') res = c.execute('select * from members') for row in res: print row