一、数据结构
我们必须知道,一个网页上存在许多链接,并且如果已经爬取过的页面是不需要再重复进行爬取的,那么爬虫就需要判断,①这个页面是否曾经被爬取过②页面上的这些链接爬取的顺序
解决问题一:
Python自从2.3后提供了一种名为集合(set)的数据结构,和数学上的集合一样,支持交、并、差等运算,set是一种无序且不包含重复元素的数据结构
所以我们可以把爬取过的URL扔进集合中,然后对目前的URL进行判定是否在集合中,如果存在即爬取过,便不再重复爬取
# encoding: utf-8
a = set('abracadabra')
b = set('alacazam')
print(a)
print(b)
c = a | b
print(c)
d = a - b
print(a-b)
e = a & b
print(e)
f = a ^ b
print(f)
可以得到如下结果
{'r', 'd', 'b', 'c', 'a'}
{'l', 'm', 'z', 'c', 'a'}
{'r', 'z', 'd', 'b', 'c', 'a', 'l', 'm'}
{'b', 'd', 'r'}
{'c', 'a'}
{'r', 'z', 'd', 'b', 'l', 'm'}
解决问题二:
Python中提供双端队列(Double-ended queue)简称deque,在collections模块中包含deque类型和defaultdict类型
# encoding: utf-8
from collections import deque
queue = deque(["txb", "hsx", "hxp"])
queue.append("zyz")
queue.append("wcy")
print(queue.popleft())
print(queue)
得到如下结果
txb
deque(['hsx', 'hxp', 'zyz', 'wcy'])
二、一次请求
我们知道在百度搜索一次以后关键词在什么位置,所以我们可以自己构造这次请求来获得这个请求页面
# encoding: utf-8
import urllib
import urllib.request
data = {}
data['word'] = 'one peace'
url_values = urllib.parse.urlencode(data)
url = "http://www.baidu.com/s?"
full_url = url+url_values
a = urllib.request.urlopen(full_url)
data = a.read()
data = data.decode('UTF-8')
print(data)
# 打印出网址:
a.geturl()
可以看出我们已经得到了,我们再尝试通过Google访问一下
# encoding: utf-8
import urllib
import urllib.request
headers={
'User-Agent':'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/34.0.1847.137 Safari/537.36 LBBROWSER'
}
data = {}
data['q'] = 'one peace'
url_values = urllib.parse.urlencode(data)
url = "https://www.google.com.hk/search?hl=zh-CN&"
full_url = url+url_values
request = urllib.request.Request(full_url, headers = headers)
a = urllib.request.urlopen(request)
data = a.read()
data = data.decode('UTF-8')
print(data)
# 打印出网址:
a.geturl()
三、正则表达式
原来我发过一篇读书笔记《正则表达式必知必会》,是关于正则表达式最基础的知识,这个部分着重讲解Python中的正则表达式(re模块)
re模块中一些重要的函数
compile(pattern[,flags]) 根据包含正则表达式的字符串创建模式对象
re.compile将正则表达式转换为模式对象,以实现更有效率的匹配
模式对象本身也有search和match函数,可以使用pat.search(string)
search(pattern, string[, flags]) 在字符串中寻找模式
search会在给定字符串中寻找第一个匹配给定正则表达式的子字符串
match(pattern, string[, flags]) 在字符串的开始处匹配模式
match会在给定字符串的开头匹配正则表达式
split(pattern, string[, maxsplit=0]) 根据模式的匹配项来分割字符串
split会根据模式的匹配项来分割字符串,返回值是子字符串的列表
findall(pattern, string) 列出字符串中模式的所有匹配项
findall以列表形式返回给定模式的所有匹配项
sub(pat, repl, string[, count=0]) 将字符串中所有pat的匹配项用repl替换
sub使用给定的替换内容将匹配模式的子字符串替换掉
escape(string) 将字符串中所有特殊正则表达式字符转义
escape对字符串中所有可能被解释为正则运算符的字符进行转义
在这里我只是简单介绍一下,正则表达式还得需要自己深入实践才能有所收获,关于一些常见的方法和参数,给出一个博客链接,大家去看他的文章
rlovep的博客