生成器与迭代器区别: 容器是一种把多个元素组织在一起的数据结构, 容器中的元素可以逐个地迭代获取,可以用in,not in 关键字判断元素是否包含在容器中。 通常这类数据结构把所有的元素存储在内存中(也有一些特例,并不是所有的元素都放在内存,比如迭代器和生成器对象)在python中, 常见的容器对象有:
list,deque,...
set,fronzensets,...
dict,defaultdict,OrderedDict,Counter,...
tuple,namedtuple,...
str 容器比较容易理解,因为你可以把它看做是一个盒子,一栋房子、一个柜子,里面可以塞任何东西。从技术角度来说,当它可以用来询问某个 元素是否包含在其中时,那么这个对象就可以认为是一个容器,比如list,set,tuples都是容器对象: 尽管绝大多数容器都提供了某种方式来获取其中的每一个元素,但这并不是容器本身提供的能力,而是可迭代对象赋予了容器这种能力, 当然并不是所有的容器都是可迭代的,比如:Bloom Filter,虽然Bloom Filter可以用来检测某个元素是否包含在容器中,但是并不能从 容器中获取其中的一个值,因为Bloom filter压根就没把元素扫描在容器中,而是通过一个散列函数映射成一个值保存在数组中。
可迭代对象:
刚才说过,很多容器都是可迭代对象,此外还有跟多的对象同样可是可迭代对象,比如打开状态的files、socket等等,
但凡是可以返回一个迭代器的对象都可称之为可迭代对象,听起来可能有点困惑,没关系,先看一个例子:
迭代器:
它是一个带状态的对象,他能在你调用next()方法地时候返回容器中的下一个值,任何实现了__iter__和__next__()
迭代器就是实现了工厂模式的对象
class Fib:
def __init__(self):
self.prev = 0
self.curr = 1
def __iter__(self):
return self
def __next__(self):
value = self.curr
self.curr += self.prev
self.prev = value
return value
f = Fib()
生成器:
生成器是一种特殊的迭代器,这种迭代器更加优雅,不需要向上面的类一样写__iter__()和__next__()方法了,只需要一个yield
关键字,生成器一定是迭代器(反之不成立),因此任何生成器也是一一种懒加载的模式生成值。
def fib():
prev,curr = 0 ,1
while True:
yield curr
prev,curr = curr,curr+prev
装饰器:python的AOP利器
def not_null(*varnames):
def outer(func):
def inner(*args,**kwargs):
args_name = func.__code__.co_varnames
args_cnt = func.__code__.co_argcount
flag = True
for name in varnames:
index = args_name.index(name)
flag = flag and (args[index] is not None)
if not flag:
raise TypeError("somethis is None")
result = func(*args,**kwargs)
return result
return inner
return outer
yield关键字做了什么 当你的函数需要返回一个很大的元素集合,并且每个元素只需要用到一次的时候,使用yield会非常方便
web server side:
服务器必须做两件事情:
一个environ字典和一个start_response函数:
iterable=app(environ,start_response)
for data in iterable:
#send data to client
WSGI PEP333 WSGI中分块传输大文件,使用yield:(rhodesmill.org/brandon/2013/chunked-wsgi)
后续:
http://benosteen.wordpress.com
My swiss army toolkit for distributed/multiproesssing systems