python爬⾍之()参数
⽂章⽬录
前情回顾
⽬前反爬总结
基于User-Agent反爬
1、发送请求携带请求头: headers={'User-Agent':'Mozilla/5.0 xxxxxx'}
2、多个请求随机切换User-Agent
1、定义列表存放⼤量User-Agent,使⽤random.choice()每次随机选择
2、定义py⽂件存放⼤量User-Agent,使⽤random.choice()每次随机选择
3、使⽤fake_useragent模块每次访问随机⽣成User-Agent
# sudo pip3 install fake_useraget
*from fake_useragent import UserAgent
* ua = UserAgent()
* user_agent = ua.random
*print(user_agent)
响应内容前端JS做处理反爬
1、html页⾯中可匹配出内容,程序中匹配结果为空(html格式化)
*响应内容中嵌⼊js,对页⾯结构做了⼀定调整导致,通过查看⽹页源代码,格式化输出查看结构,更改xpath或者正则测试2、如果数据出不来可考虑更换 IE 的User-Agent尝试,数据返回最标准
请求模块总结
urllib库使⽤流程
# 编码
params ={
'':'',
'':''
}
params = urllib.parse.urlencode(params)
url = baseurl + params
# 请求
request = quest.Request(url,headers=headers)
response = quest.urlopen(request)
html = ad().decode('utf-8')
requests模块使⽤流程
baseurl ='tieba.baidu/f?'
html = (url,headers=headers).content.decode('utf-8','ignore')
响应对象res属性
< :字符串
res.status_code :HTTP响应码
res.url :实际数据URL地址
解析模块总结
正则解析re模块
import re
pattern = repile(r'正则表达式',re.S)
r_list = pattern.findall(html)
lxml解析库
from lxml import etree
parse_html = etree.)
r_list = parse_html.xpath('xpath表达式')
xpath表达式
匹配规则
1、节点对象列表
# xpath⽰例: //div、//div[@class="student"]、//div/a[@title="stu"]/span
2、字符串列表
# xpath表达式中末尾为: @src、@href、text()
xpath⾼级
1、基准xpath表达式:得到节点对象列表
2、for r in[节点对象列表]:
username = r.xpath('./xxxxxx')
# 此处注意遍历后继续xpath⼀定要以: . 开头,代表当前节点
写程序注意
# 最终⽬标: 不要使你的程序因为任何异常⽽终⽌
1、页⾯请求设置超时时间,并⽤try捕捉异常,超过指定次数则更换下⼀个URL地址
2、所抓取任何数据,获取具体数据前先判断是否存在该数据,可使⽤列表推导式# 多级页⾯数据抓取注意
1、主线函数:解析⼀级页⾯函数(将所有数据从⼀级页⾯中解析并抓取)
增量爬⾍如何实现
1、数据库中创建指纹表,⽤来存储每个请求的指纹
2、在抓取之前,先到指纹表中确认是否之前抓取过
Chrome浏览器安装插件
安装⽅法
# 在线安装
1、下载插件- google访问助⼿
2、安装插件- google访问助⼿: Chrome浏览器-设置-更多⼯具-扩展程序-开发者模式-拖拽(解压后的插件)
3、在线安装其他插件-打开google访问助⼿- google应⽤商店-搜索插件-添加即可
# 离线安装
1、下载插件- 重命名为 xxx.zip
2、输⼊地址: chrome://extensions/打开-开发者模式
3、拖拽插件(或者解压后⽂件夹)到浏览器中
4、重启浏览器,使插件⽣效
今⽇笔记
链家⼆⼿房案例(xpath)
实现步骤
确定是否为静态
打开⼆⼿房页⾯->查看⽹页源码->搜索关键字
xpath表达式
1、基准xpath表达式(匹配每个房源信息节点列表)
此处滚动⿏标滑轮时,li节点的class属性值会发⽣变化,通过查看⽹页源码确定xpath表达式
//ul[@class="sellListContent"]/li[@class="clear LOGVIEWDATA LOGCLICKDATA"]
2、依次遍历后每个房源信息xpath表达式
*名称:'.//a[@data-el="region"]/text()'
# 户型+⾯积+⽅位+是否精装
info_list ='.//div[@class="houseInfo"]/text()'[0].strip().split('|')
*户型: info_list[1]
*⾯积: info_list[2]
*⽅位: info_list[3]
*精装: info_list[4]
*楼层:'.//div[@class="positionInfo"]/text()'
*区域:'.//div[@class="positionInfo"]/a/text()'
*总价:'.//div[@class="totalPrice"]/span/text()'
*单价:'.//div[@class="unitPrice"]/span/text()'
代码实现
import requests, time, random
from fake_useragent import UserAgent
from lxml import etree
class LianJiaSpider:
def__init__(self):
self.url ="zz.lianjia/ershoufang/pg{}/"
self.blag=1
# 随机headers
def get_headers(self):
agent = UserAgent().random
headers ={"User-Agent": agent}
return headers
# 请求
def get_html(self, url):
#请求三次.每次请求时间最多为5秒
#请求三次.每次请求时间最多为5秒
if self.blag<=3:
try:
res = (url=url, _headers(),timeout=5)
#
html = t.decode()
return html
except Exception as e:
print(e)
self.blag+=1
<_html(url)
# 解析
def parse_html(self, url):
html = _html(url)
if not html:
return None
p = etree.HTML(html)
# 基准xpath表达式 -30个房源节点对象列表
h_list = p.xpath('//ul[@class="sellListContent"]/li[@class="clear LOGVIEWDATA LOGCLICKDATA"]')
for h in h_list:
item ={}
# 名称
item["name"]=(h.xpath('.//a[@data-el="region"]/text()')[0]if h.xpath('.//a[@data-el="region"]/text()')else None) # 户型+⾯积+⽅位+是否精装
info_list = h.xpath('.//div[@class="houseInfo"]/text()')
if info_list:
L = info_list[0].split("|")
if len(L)==5:
item["model"]= L[1].strip()
item["area"]= L[2].strip()
item["direction"]= L[3].strip()
item["perfect"]= L[4].strip()
else:
item["model"]= item["area"]= item["direction"]= item["perfect"]=None
else:
item["model"]= item["area"]= item["direction"]= item["perfect"]=None
# 楼层
item["floor"]=(h.xpath('.//div[@class="positionInfo"]/text()')[0]if h.xpath('.//div[@class="positionInfo"]/text()')else None) # 区域
item["address"]=(h.xpath('.//div[@class="positionInfo"]/a/text()')[0]if h.xpath('.//div[@class="positionInfo"]/a/text()')else None) # 总价
item["total"]=(h.xpath('.//div[@class="totalPrice"]/span/text()')[0]+"万"if h.xpath('.//div[@class="totalPrice"]/span/text()')else None) # 单价
item["unit"]=(h.xpath('.//div[@class="unitPrice"]/span/text()')[0]if h.xpath('.//div[@class="unitPrice"]/span/text()')else None) print(item)
# 保存
def save_html(self):
pass
def run(self):
for i in range(1,20):
url=self.url.format(i)
self.parse_html(url)
# time.sleep(random.randint(1,3))
#没抓取⼀页要初始化self.blag
self.blag=1
if __name__ =='__main__':
l = LianJiaSpider()
l.run()
百度贴吧图⽚抓取
⽬标思路
⽬标
抓取指定贴吧所有图⽚
思路
1、获取贴吧主页URL,下⼀页,到不同页的URL规律
2、获取1页中所有帖⼦URL地址:[帖⼦链接1,帖⼦链接2,...]
3、对每个帖⼦链接发请求,获取图⽚URL
4、向图⽚的URL发请求,以wb⽅式写⼊本地⽂件
实现步骤
贴吧URL规律
tieba.baidu/f?kw=??&pn=50
xpath表达式
1、帖⼦链接xpath
//div[@class="t_con cleafix"]/div/div/div/a/@href
2、图⽚链接xpath
//div[@class="d_post_content j_d_post_content clearfix"]/img[@class="BDE_Image"]/@src
3、视频链接xpath
//div[@class="video_src_wrapper"]/embed/@data-video
# 注意: 此处视频链接前端对响应内容做了处理,需要查看⽹页源代码来查看,复制HTML代码在线格式化代码实现
from urllib import parse
import requests, time, random
from fake_useragent import UserAgent
from lxml import etree
class TieBa:
def__init__(self):
self.url ="tieba.baidu/f?"
#如果各种数据及其逻辑没有问题,则需将浏览器标识改为IE浏览器
self.headers ={"User-Agent":'Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.0) '}
# UserAgent().random
# 请求
def get_html(self, url,params=None):
html = (url=url,params=params, headers=self.headers).content.decode("utf-8","ignore") return html
# xpath解析
def xpath_html(self, html, xpath_db):
p = etree.HTML(html)
r_list = p.xpath(xpath_db)
return r_list
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论