刚刚写了一个爬虫,尝试读取豆瓣电影的评价及相关信息,并下载电影的一个海报图片,因为我自己的电脑是双核,所以,为了提高效率,利用cluster开了两个进程来跑,效率还可以,其中遇到了几个问题:
1、是关于链接地址的问题,因为之前没有写过类似的程序,所以没思路,当时我有两种想法(包括现在).第一种就是固定住一个链接地址,然后不听的变换页面的id,比如:http://movie.douban.com/subject/10485647/
每次只要替换掉id就可以了,但是这样的话,貌似效率不高,所以我舍弃了这种方法。第二种方法就是以一个固定的链接地址作为程序的入口,在读取完该页面的信息之后,再查找这个页面的所有的链接,找到有跟当前页面一样的链接,然后存入一个数组,接着循环爬这些地址页面,这样,避免了猜测链接地址和不必要的请求,但是带来的问题是因为每个页面的链接数不定,所以每爬到一个页面,盛放链接地址的数组就会增加很多,最终导致这个数组无限大,而内存又有点不够用了,所以这里不知道大家有没有什么好的想法。
2、关于访问受限的问题,因为知道很多网站为了防止爬虫爬取,如果发先在短时间内有大量的来自于同一ip的请求的话,这时该网站一般都是禁止ip访问。我这里的做法是每次请求都去换useragent,来达到尽量模仿浏览器行为的目的。其次是每次请求的时候都去伪造ip,这个伪造ip的方法就是在request的header里面加入x-forward-for属性,其实这么做完全是寄希望于对方的网站在做ip检查时的bug。其实如果还是担心ip被禁止的话,还可以限制爬取的频率,即多长时间发送一次请求,但这又在一定程度上影响了效率。在这里也想问问大家,在这个问题上都是怎么处理的。
3、遇到的地三个问题,可能是因为我没有做请求频率的限制,即同一时间发送了很多的请求出去(如前所说,将所有链接存入数组,然后循环这个数组发送请求。但是却没有发现豆瓣封掉我的ip).加上每个请求都会下载该页面的电影的一张海报下来,所以必然导致了我的I/O开销的增大。以至于后来我发现程序报错:Error: connect EMFILE,这明显是因为系统文件最大连接数限制造成的。所以按照网上的说法,是改掉这个值。但是我觉得这不能从根本上解决问题,所以,这里也想问问大家,这个问题应该如何解决。
4、综上:希望大家多多指点。