文档章节

python 迭代器与生成器

eddy_linux
 eddy_linux
发布于 2015/11/06 00:51
字数 1317
阅读 160
收藏 3
一、迭代器
对于Python 列表的 for 循环,他的内部原理:查看下一个元素是否存在,如果存在,则取出,如果不存在,则报异常 StopIteration。(python内部对异常已处理)
class listiterator(object)
 |  Methods defined here:
 |  
 |  __getattribute__(...)
 |      x.__getattribute__('name') <==> x.name
 |  
 |  __iter__(...)
 |      x.__iter__() <==> iter(x)
 |  
 |  __length_hint__(...)
 |      Private method returning an estimate of len(list(it)).
 |  
 |  next(...)
 |      x.next() -> the next value, or raise StopIteration

listiterator
迭代:重复做一件事
iterable:可迭代对象
          支持每次返回自己所包含的一个成员对象
          对象实现了__iter__方法
          序列类型:list、str、tuple
          非序列类型:dict、file
          用户自定义包含了__iter__()或__getitem__()方法的类
li = [1,2,3,4,5,6,7]
['__add__', '__class__', '__contains__', '__delattr__', '__delitem__', '__delslice__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__', '__getitem__', '__getslice__', '__gt__', '__hash__', '__iadd__', '__imul__', '__init__', '__iter__', '__le__', '__len__', '__lt__', '__mu__', '__ne__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__reversed__', '__rmul__', '__setattr__', '__setitem__', '__setslice__', '__sizeof__', '__str__', '__subclasshook__', 'append', 'count', 'extend', 'index', 'insert', 'pop', 'remove', 'reverse', 'sort']  
包含了__iter__
li.__iter__()
<listiterator object at 0x10ecf90>
返回了一个迭代器
也就说明了li是一个可迭代对象
>>> i1 = li.__iter__()
>>> i1.next()
1
>>> i1.next()
2
>>> i1.next()
3
>>> i1.next()
4
>>> i1.next()
5
>>> i1.next()
6
>>> i1.next()
7
>>> i1.next()
Traceback (most recent call last):
  File "<input>", line 1, in <module>
StopIteration
遍历完成后抛出异常,说明迭代结束,他不会从头在进行迭代
对象有迭代器的话我们就不需要手动再建立遍历
i2 = iter(li)
for循环可用于任何迭代对象

二、列表解析
    列表解析是python迭代机制的一种已用
    根据已有列表快速生成新列表的方式
>>> li = [1,2,3,4,5]
>>> 
>>> l1 = []
>>> for i in li:
...     l1.append(i**2)
...     
... 
>>> l1
[1, 4, 9, 16, 25]
列表解析语法
[ expression for iter_var in iterable ]

>>> l2 = [ i**2 for i in li ]
>>> l2
[1, 4, 9, 16, 25]
[ expression for iter_var in iterable if cond_expr ]
>>> l3 = [ i**2 for i in li if i >= 3 ]
>>> l3
[9, 16, 25]
可对于列表生成中直接应用列表解析器
这里就不用先生成一个1,10的列表
>>> for i in [ i**2 for i in range(11) ]:print i/2.0
... 
0.0
0.5
2.0
4.5
8.0
12.5
18.0
24.5
32.0
40.5
50.0
还可以更复杂应用
>>> for i in [ i**2 for i in range(11) if i %2 == 0]:print i/2.00
... 
0.0
2.0
8.0
18.0
32.0
50.0
举例:
取出/var/log/下面以.log结尾的文件
常规方法:
filelist = os.listdir('/var/log')
str.endswith('.log')
filelist2 = [ i for i in filelist   if i.endswith('.log') ] 
>>> filelist = os.listdir('/var/log')
>>> filelist2 = [ i for i in filelist   if i.endswith('.log') ] 
>>> filelist2
['gshell.log', 'mysqld.log', 'vmstart.log', 'repair.log', 'boot.log', 'ntp.log', 'dracut.log', 'yum.log', 'rdate.log']         

列表解析
filelist2 = [ i for i in  os.listdir('/var/log') if i.endswith('.log') ]

取出/etc目录下的是目录的文件
filelist3 = [ i for i in os.listdir('/etc') if os.path.isdir('/etc/%s' %i) ]
['depmod.d', 'rc4.d', 'audit', 'ld.so.conf.d', 'modprobe.d', 'backup', 'rc5.d', 'rc6.d', 'iproute2', 'bash_completion.d', 'security', 'yum', 'nginx', 'blkid', 'logrotate.d', 'rc0.d', 'ConsoleKit', 'lsb-release.d', 'statetab.d', 'rsyslog.d', 'sudoers.d', 'sasl2', 'ssl', 'pkcs11', 'redhat-lsb', 'skel', 'polkit-1', 'fonts', 'chkconfig.d', 'rc1.d', 'sysconfig', 'makedev.d', 'cron.monthly', 'udev', 'setuptool.d', 'lvm', 'rabbitmq', 'ssh', 'selinux', 'rpm', 'subversion', 'ppp', 'gtk-2.0', 'sensu', 'pango', 'cron.d', 'audisp', 'pcmcia', 'popt.d', 'dracut.conf.d', 'pam.d', 'alternatives', 'xinetd.d', 'rc3.d', 'NetworkManager', 'abrt', 'gnupg', 'dbus-1', 'terminfo', 'ntp', 'pki', 'hal', 'cron.daily', 'dhcp', 'yum.repos.d', 'init', 'plymouth', 'libreport', 'X11', 'pm', 'init.d', 'alsa', 'openldap', 'rc.d', 'rwtab.d', 'gcrypt', 'xdg', 'kdump-adv-conf', 'rc2.d', 'cron.weekly', 'postfix', 'scl', 'cron.hourly', 'opt','acpi', 'default', 'profile.d', 'prelink.conf.d', 'event.d', 'ansible'


三、生成器
生成器表达式并不真正创建数字列表,而是返回一个生成器对象,每次计算出一个条目后,把这个条目产生出来(yield)
使用了惰性计算或叫做延迟求值的机制
语法:
(exor for iter_var in iterable)
(exor for iter_var in iterable if cond_expr)
和列表解析区别在于小括号
是对列表解析的一种补充
range不是生成器 和 xrange 是生成器
类比列表解析和生成器
readlines不是生成器 和 xreadlines 是生成器
>>> print range(10)
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
>>> print xrange(10)
xrange(10)

(i**2 for i in range(11))这是一个对象
for i in (i**2 for i in range(11)):print i/2
生成器内部基于yield创建,即:对于生成器只有使用时才创建,从而不避免内存浪费

enumerate:
range可在非完备遍历中用于生成所以偏移,而非偏移处的元素
如果同时需要偏移索引和偏移元素,则可以使用enumerate()函数
此函数返回一个生成器对象
例如:返回文件行号和行值
>>> with open('/var/log/messages','r') as obj:
...     E = enumerate(obj)
...     for i in E:
...         print i 
...         
...     
... 
(0, 'Nov 15 03:22:01 iZ23tags5s2Z rsyslogd: [origin software="rsyslogd" swVersion="5.8.10" x-pid="813" x-info="http://www.rsyslog.com"] rsyslogd was HUPe
d\n')
(1, "Nov 15 13:14:24 iZ23tags5s2Z abrt: detected unhandled Python exception in '3.py'\n")
(2, 'Nov 15 13:23:34 iZ23tags5s2Z abrt: detected unhandled Python exception\n')
(3, 'Nov 16 00:37:05 iZ23tags5s2Z yum[22345]: Installed: pygobject2-2.20.0-5.el6.x86_64\n')
(4, 'Nov 16 00:37:06 iZ23tags5s2Z yum[22345]: Installed: python-pygments-1.1.1-1.el6.noarch\n')
(5, 'Nov 16 00:37:06 iZ23tags5s2Z yum[22345]: Installed: pycairo-1.8.6-2.1.el6.x86_64\n')
(6, 'Nov 16 00:37:07 iZ23tags5s2Z yum[22345]: Installed: pygtk2-2.16.0-3.el6.x86_64\n')
(7, 'Nov 16 00:37:07 iZ23tags5s2Z yum[22345]: Installed: bpython-0.9.7.1-3.el6.noarch\n')
有如下列表:
    [13, 22, 6, 99, 11] 
请按照一下规则计算:
13 和 22 比较,将大的值放在右侧,即:[13, 22, 6, 99, 11]
22 和 6 比较,将大的值放在右侧,即:[13, 6, 22, 99, 11]
22 和 99 比较,将大的值放在右侧,即:[13, 6, 22, 99, 11]
99 和 42 比较,将大的值放在右侧,即:[13, 6, 22, 11, 99,]
 
13 和 6 比较,将大的值放在右侧,即:[6, 13, 22, 11, 99,]
li = [13, 22, 6, 99, 11]
for i in range(1,5):    
    for m in range(len(li)-i): 
        if li[m] > li[m+1]:
            temp = li[m+1]
            li[m+1] = li[m]
            li[m] = temp



© 著作权归作者所有

共有 人打赏支持
eddy_linux
粉丝 18
博文 135
码字总数 188789
作品 0
成都
程序员
Python3+迭代器与生成器

转载Python3 迭代器与生成器 迭代器 迭代是Python最强大的功能之一,是访问集合元素的一种方式。 迭代器是一个可以记住遍历的位置的对象。 迭代器对象从集合的第一个元素开始访问,直到所有的...

xinet
2017/08/12
0
0
Python的三大神器,你知道是哪三大吗?史上最详细的入门教程!

Python的三大神器:装饰器.迭代器与生成器!这就是Python的三大神器,好了废话不多说。直接来上干货吧! 生成器 仅仅拥有生成某种东西的能力,如果不用next方法是获取不到值得。 创建一个生成...

q1622479435
06/08
0
0
Python中的迭代器与生成器

container.iter() 和 iterator.next() 迭代器就是一个有 next() 方法的对象。当需要下一个数据时,调用它的 next() 方法就可以获得。在Python2中,这个方法被命名为 next() 。但在Python3中新...

lionets
2013/11/21
0
0
更深入的理解 Python 中的迭代

深入探讨 Python 的 循环来看看它们在底层如何工作,以及为什么它们会按照它们的方式工作。 Python 的 循环不会像其他语言中的 循环那样工作。在这篇文章中,我们将深入探讨 Python 的 循环来...

01%
05/26
0
0
关于Python中的yield

在介绍yield前有必要先说明下Python中的迭代器(iterator)和生成器(constructor)。 一、迭代器(iterator) 在Python中,for循环可以用于Python中的任何类型,包括列表、元祖等等,实...

劲风online
2015/07/20
0
0

没有更多内容

加载失败,请刷新页面

加载更多

下一页

49.Nginx防盗链 访问控制 解析php相关 代理服务器

12.13 Nginx防盗链 12.14 Nginx访问控制 12.15 Nginx解析php相关配置(502的问题) 12.16 Nginx代理 扩展 502问题汇总 http://ask.apelearn.com/question/9109 location优先级 http://blog....

王鑫linux
58分钟前
0
0
Nginx防盗链、访问控制、解析php相关配置、Nginx代理

一、Nginx防盗链 1. 编辑虚拟主机配置文件 vim /usr/local/nginx/conf/vhost/test.com.conf 2. 在配置文件中添加如下的内容 { expires 7d; valid_referers none blocked server_names *.tes......

芬野de博客
今天
0
0
spring EL 和资源调用

资源调用 import org.springframework.beans.factory.annotation.Value;import org.springframework.context.annotation.PropertySource;import org.springframework.core.io.Resource;......

Canaan_
今天
1
0
memcached命令行、memcached数据导出和导入

一、memcached命令行 yum装telnet yum install telent 进入memcached telnet 127.0.0.1 11211 命令最后的2表示,两位字节,30表示过期时间(秒) 查看key1 get key1 删除:ctrl+删除键 二、m...

Zhouliang6
今天
0
0
Linux定时备份MySQL数据库

做项目有时候要备份数据库,手动备份太麻烦,所以找了一下定时备份数据库的方法 Linux里有一个 crontab 命令被用来提交和管理用户的需要周期性执行的任务,就像Windows里的定时任务一样,用这...

月夜中徘徊
今天
1
1

没有更多内容

加载失败,请刷新页面

加载更多

下一页

返回顶部
顶部