1. 开发者工具检查网页
Chrome浏览器→“更多工具”→ “开发者工具”(F12快捷键)
Chrome提供的开发者工具如下:
-
Elements: 允许用户从浏览器的角度来观察网页,用户可以借此看到Chrome渲染页面所需要的HTML、CSS和DOM(Document
Object Model)对象。
(检查和编辑页面的HTML与CSS:选中并双击元素就可以编辑元素.
e.x.将“python”这几个字去掉,右键该元素,选择“Delete Element”) -
Network:可以看到网页向服务气请求了哪些资源、资源的大小以及加载资源的相关信息。此外,还可以查看HTTP的请求头、返回内容等。
-
Source:即源代码面板,主要用来调试JavaScript。
-
Console:即控制台面板,可以显示各种警告与错误信息。在开发期间,可以使用控制台面板记录诊断信息,或者使用它作为shell在页面上与JavaScript交互。
-
Performance:使用这个模块可以记录和查看网站生命周期内发生的各种事情来提高页面运行时的性能。
-
Memory:这个面板可以提供比Performance更多的信息,比如跟踪内存泄漏。
-
Application:检查加载的所有资源。
-
Security:即安全面板,可以用来处理证书问题等。
2. 基本应用
一个网络爬虫程序最普遍的过程:
1.访问站点;
2.定位所需的信息;
3.得到并处理信息。
(1)request库
import requests
url = 'https://www.python.org/dev/peps/pep-0020/'
res = requests.get(url)
text = res.text#
## 爬取python之禅并存入txt文件
with open('zon_of_python.txt', 'w') as f:
f.write(text[text.find('<pre')+28:text.find('</pre>')-1])
print(text[text.find('<pre')+28:text.find('</pre>')-1])
(2) urllib
包含功能:向网络请求数据、处理cookie、自定义请求头等
urllib的request模块可以非常方便地抓取URL内容,也就是发送一个GET请求到指定的页面,然后返回HTTP的响应:
import urllib
url = 'https://www.python.org/dev/peps/pep-0020/'
res = urllib.request.urlopen(url).read().decode('utf-8')
print(res[res.find('<pre')+28:res.find('</pre>')-1])
3.实践+拓展
(1)解决由于反爬虫措施存在而遇到的爬虫时返回状态码418问题
搜索引擎本质上也是一个爬虫,而我们在做的只是低配版的而已,浏览器里通过开发者模式可以看到有用户代理,头等信息,那么我们也使用requests库来添加用户代理来尝试一下。
import random
def get_response(url): #设置代理服务器解决418
user_list = (
{'user-agent': "Mozilla/5.0 (Macintosh; Intel Mac OS X 10.6; rv2.0.1) Gecko/20100101 Firefox/4.0.1"},
{'user-agent': "Mozilla/5.0 (Windows NT 6.1; rv2.0.1) Gecko/20100101 Firefox/4.0.1"},
{'user-agent': "Opera/9.80 (Macintosh; Intel Mac OS X 10.6.8; U; en) Presto/2.8.131 Version/11.11"},
{'user-agent': "Opera/9.80 (Windows NT 6.1; U; en) Presto/2.8.131 Version/11.11"},
{'user-agent': "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_7_0) AppleWebKit/535.11 (KHTML, like Gecko) Chrome/17.0.963.56 Safari/535.11"}
)
user_agent = random.choice(user_list)
response = requests.get(url, headers=user_agent)
content=response.text
return content
(2)解决TOP250电影有多个网页的问题,找到网页链接规律:为’https://movie.douban.com/top250?start=’ + 页码数(其中每页25部电影)+ ‘&filter=’,采用循环获取url
for i in range(0,250,25):
url='https://movie.douban.com/top250?start=' + str(i) + '&filter='
#print(url)
(3)提取每一个影片内容:
soup = BeautifulSoup(content, “html.parser”):创建BeautifulSoup对象,content为页面内容,html.parser是一种页面解析器;
class_=‘item’:找到能够完整提取出一个影片内容的项,即页面中所有样式是item类的div。
soup = BeautifulSoup(content, "html.parser")
for item in soup.find_all('div',class_='item'):#找到每一个影片项
(4)解析出片名以及图片地址——正则表达式
- re.compile()&re.find_all()
- re.compile()方法可以将正则字符串编译成正则表达式对象,以便在后面的匹配中复用。
re.compile(pattern[, flags])
- re.compile()中可以传入忽略换行等匹配模式,这样在search()、findall()方法中就不需要额外传入了。
findall(patern, string, flags=0)
- re.findall()方法有2种表达方式:
import re
content = 'one1two22three333four4444'
pattern = re.compile(r'\d+')
print('===方法1:===')
result1 = re.findall(pattern, content)
print(result1)
print('===方法2===')
result2 = pattern.findall(content)
print(result2)
- re.find_all()&.*?&re.S
- #参数有re.S,不会对\n进行中断
#a.b,匹配从a为开始到后面b为结束的所有内容
#a.?b,遇到a开始和b结束就进行截取,因此截取多次符合的结果,中间没有字符也会被截取
#a(.*?)b 与上面一样,只是与上面的相比多了一个括号,只保留括号的内容,即a与b之间的内容
以下代码可提取出src=“”引号中的内容
findImg=re.compile(r'<img.*src="(.*?)"',re.S)
img=re.findall(findImg,item)
最终代码汇总:
import requests
import re
from bs4 import BeautifulSoup
import random
def get_response(url): #设置代理服务器解决418
user_list = (
{'user-agent': "Mozilla/5.0 (Macintosh; Intel Mac OS X 10.6; rv2.0.1) Gecko/20100101 Firefox/4.0.1"},
{'user-agent': "Mozilla/5.0 (Windows NT 6.1; rv2.0.1) Gecko/20100101 Firefox/4.0.1"},
{'user-agent': "Opera/9.80 (Macintosh; Intel Mac OS X 10.6.8; U; en) Presto/2.8.131 Version/11.11"},
{'user-agent': "Opera/9.80 (Windows NT 6.1; U; en) Presto/2.8.131 Version/11.11"},
{'user-agent': "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_7_0) AppleWebKit/535.11 (KHTML, like Gecko) Chrome/17.0.963.56 Safari/535.11"}
)
user_agent = random.choice(user_list)
response = requests.get(url, headers=user_agent)
content=response.text
return content
order = 0
data = []
for i in range(0,250,25):
url='https://movie.douban.com/top250?start=' + str(i) + '&filter='
#print(url)
soup = BeautifulSoup(get_response(url), "html.parser")
findTitle=re.compile(r'<img.*alt="(.*?)" class="')
findImg=re.compile(r'<img.*src="(.*?)"',re.S)
#参数有re.S,不会对\n进行中断
#a.*b,匹配从a为开始到后面b为结束的所有内容
#a.*?b,遇到a开始和b结束就进行截取,因此截取多次符合的结果,中间没有字符也会被截取
#a(.*?)b 与上面一样,只是与上面的相比多了一个括号,只保留括号的内容,即a与b之间的内容
for item in soup.find_all('div',class_='item'):#找到每一个影片项
item = str(item)
order = order + 1
#找到影片图片<img……src=“”
#e.x.:
#<img width="100" alt="蝙蝠侠:黑暗骑士" src="https://img3.doubanio.com/view/photo/s_ratio_poster/public/p462657443.webp" class="">
title=re.findall(findTitle,item)#提取出alt=“”引号中的内容
img=re.findall(findImg,item) #提取出src=“”引号中的内容
print(order,title,img)
输出结果: