2012-03-03 53 views
10

我有一个网站,我的抓取工具需要遵循一个序列。因此,例如,它需要先去a1,b1,c1,然后才能开始执行a2等。a,b和c中的每一个都由不同的解析函数处理,并且相应的url在Request对象中创建并产生。下面大致说明我正在使用的代码:Scrapy似乎没有做DFO

class aspider(BaseSpider): 

    def parse(self,response): 
     yield Request(b, callback=self.parse_b, priority=10) 

    def parse_b(self,response): 
     yield Request(c, callback=self.parse_c, priority=20) 

    def parse_c(self,response) 
     final_function()   

然而,我发现,爬的序列似乎是A1,A2,A3,B1,B2,B3,C1,C2,C3这是奇怪的因为我认为Scrapy应该首先保证深度。

该顺序不一定是严格的,但我所抓取的网站有一个限制,所以Scrapy需要在b级5个级别之前尽快开始抓取级别c。这怎么能实现?

+0

如果您忽略优先级设置,会发生什么情况? – 2012-03-05 11:34:54

+0

同样,我试图增加优先考虑的方式是尝试查看是否可以影响结果。 – Mishari 2012-03-05 16:20:21

+1

Srcrapy不会使用BaseSpider自动爬网。由于您使用的是“BaseSpider”,因此显示代码您非常重要请求a1,b1,c1,a2,b2,c2(有些可能由“Start-Urls”设置...不仅仅是'b, c“。 – wuliang 2012-05-08 05:09:43

回答

8

深度优先搜索你所描述的正是:

search as deep into a's as possible before moving to b's 

要改变Scrapy做广度优先搜索(A1,B1,C1,A2,等...),变化这些设置:

DEPTH_PRIORITY = 1 
SCHEDULER_DISK_QUEUE = 'scrapy.squeue.PickleFifoDiskQueue' 
SCHEDULER_MEMORY_QUEUE = 'scrapy.squeue.FifoMemoryQueue' 

*发现在doc.scrapy.org FAQ

+0

这个答案是不正确的。在OP的例子中,DFS是'(a1,b1 ,c1,a2,...)'而BFS是'(a1,a2,a3,b1,b2,b3,...)'。Scrapy不使用真正的DFS,请参阅打开的[GitHub问题](https: //github.com/scrapy/scrapy/issues/1739)。 – JayStrictor 2017-01-23 22:25:22

1

我相信你都注意到深度优先和广度优先搜索算法之间的差异(参见维基百科上的两个信息。)

Scrapy必须改变使用的算法的能力:

“默认情况下,Scrapy使用LIFO队列来存储挂起的请求,这基本上意味着它按照DFO顺序进行抓取,这个顺序在大多数情况下更加方便,如果你想抓取真正的BFO顺序,你可以通过设置以下设置:“

请参阅http://doc.scrapy.org/en/0.14/faq.html了解更多信息上。

0

Scrapy使用DFO 默认。抓取序列的原因是scrapy异步抓取页面。尽管它使用DFO,但由于网络延迟或其他原因,序列看起来不合理。