下面的Python代码是做什么的?它';这就像一个带括号的列表。

下面的Python代码是做什么的?它';这就像一个带括号的列表。,python,web-crawler,Python,Web Crawler,我正在研究用Python制作的网络爬虫,我偶然发现了一个非常简单的。但是,我不理解下面代码中突出显示的最后几行: import sys import re import urllib2 import urlparse tocrawl = [sys.argv[1]] crawled = [] keywordregex = re.compile('<meta\sname=["\']keywords["\']\scontent=["\'](.*?)["\']\s/>') linkreg

我正在研究用Python制作的网络爬虫,我偶然发现了一个非常简单的。但是,我不理解下面代码中突出显示的最后几行:

import sys
import re
import urllib2
import urlparse

tocrawl = [sys.argv[1]]
crawled = []

keywordregex = re.compile('<meta\sname=["\']keywords["\']\scontent=["\'](.*?)["\']\s/>')
linkregex = re.compile('<a\s(?:.*?\s)*?href=[\'"](.*?)[\'"].*?>')

while 1:
    crawling = tocrawl.pop(0)
    response = urllib2.urlopen(crawling)
    msg = response.read()
    keywordlist = keywordregex.findall(msg)
    crawled.append(crawling)
    links = linkregex.findall(msg)
    url = urlparse.urlparse(crawling)

    a = (links.pop(0) for _ in range(len(links))) //What does this do?

    for link in a:
        if link.startswith('/'):
            link = 'http://' + url[1] + link
        elif link.startswith('#'):
            link = 'http://' + url[1] + url[2] + link
        elif not link.startswith('http'):
            link = 'http://' + url[1] + '/' + link

        if link not in crawled:
            tocrawl.append(link)
导入系统 进口稀土 导入urllib2 导入URL解析 tocrawl=[sys.argv[1]] 爬网=[] 关键字regex=re.compile(' 也可以写成:

a = []
for _ in range(len(links)):
    a.append(links.pop(0))
编辑:

唯一的区别是当使用生成器时,它是惰性地完成的,因此项目只在通过a请求时从链接弹出。而且不是一次全部,当处理大量数据时,它会更加高效,并且如果不使用高级Python函数,就无法做到这一点。

它是a,它只是清空列表
链接
,当您在其上迭代时

他们本可以更换这个零件的

a = (links.pop(0) for _ in range(len(links))) //What does this do?

for link in a:
为此:

while links:
    link = links.pop(0)
它也会起同样的作用。但是,由于从列表末尾弹出更有效,因此这比以下两种方法都好:

links.reverse()
while links:
    link = links.pop()

当然,如果你可以按照相反的顺序跟踪链接(我不明白为什么它们需要按顺序处理),那么更有效的方法是不反转
链接
列表,而只是从末尾弹出。

它创建了一个生成器,可以从链接列表中删除对象

解释:

range(len(links))
返回一个从0到但不包括链接列表长度的数字列表。因此,如果链接包含
[“www.yahoo.com”、“www.google.com”、“www.python.org”]
,那么它将生成一个列表[0,1,2]

对于废话中的uu
,只需在列表上循环,就可以扔掉结果

links.pop(0)
从链接中删除第一项

整个表达式返回一个生成器,该生成器从链接列表的头部弹出项目

最后是python控制台中的演示:

>>> links = [ "www.yahoo.com", "www.google.com", "www.python.org "]
>>> a = (links.pop(0) for _ in range(len(links)))
>>> a.next()
'www.yahoo.com'
>>> links
['www.google.com', 'www.python.org ']
>>> a.next()
'www.google.com'
>>> links
['www.python.org ']
>>> a.next()
'www.python.org '
>>> links
[]

我不知道
a
links
有什么不同?
links
不能被迭代,我想。因此,代码只是将
links
中的所有数据迁移到
a
很抱歉再次询问,但是:我不能简单地为links中的link编写
吗?我可能需要阅读有关生成器的信息按,但到目前为止,对于这种特殊情况,我不认为有必要进行这种转换。@JakobS.不,你不能只为链接中的链接编写
,因为
links
不是一个普通的列表,它是一个regex对象。我只是尝试了一下-对我来说,它工作得很好,
键入(链接)
给了我一个
。我不知道如何反转列表,然后从列表中弹出将更有效率,您仍然从一开始就弹出,刚才列表是反转的…您不应该
pop(-1)
还是什么?(如果可能的话)
pop()
(即没有参数)从列表末尾弹出。@Inbar中的
-1
在没有参数的情况下被调用时是隐式的。从列表中间弹出效率较低,因为python必须将以下所有项在内存中向左移动一个空格。@lazyr是的,我知道这一点,我不知道-1是隐式的。现在它有意义了。感谢您的澄清。@lazyr——回答得很好。你不仅回答了问题,还提高了代码的效率和可读性。
>>> links = [ "www.yahoo.com", "www.google.com", "www.python.org "]
>>> a = (links.pop(0) for _ in range(len(links)))
>>> a.next()
'www.yahoo.com'
>>> links
['www.google.com', 'www.python.org ']
>>> a.next()
'www.google.com'
>>> links
['www.python.org ']
>>> a.next()
'www.python.org '
>>> links
[]