爬虫入门知识总结

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/apollo_miracle/article/details/84892226

爬虫的概念

爬虫就是:模拟浏览器发送网络请求,获取请求响应

爬虫的分类

聚焦爬虫:针对特定网站的爬虫

通用爬虫:搜索引擎的爬虫

爬虫的流程

url ---> 发送请求,获取响应 ----> 提取数据 ---> 保存

获取响应 ---> 提取url地址,继续请求

浏览器的请求过程

浏览器获取的数据包含:url地址对应的响应+js+css+jpg

爬虫会获取:url地址对应的响应

爬虫获取的内容和elements内容不一样,进行数据提取的时候,需要根据url地址对应的响应为准

http的重点(请求头)

user-agent:告诉对方服务器是什么客户端正在请求资源,能够达到模拟浏览器的效果

cookie:获取登录只有才能够访问的资源

python2python3中的字符串

ascii 一个字节表示一个字符

unicode 两个字节表示一个字符

utf-8 变长的编码方式,1、2、3字节表示一个字符

python2

字节类型:str,字节类型,通过decode()转化为unicode类型

str.decode()

unicode类型:unicode ,通过encode转化为str字节类型

unicode.encode("utf-8")

python3

str:unicode,通过encode() 转化为bytes

str.encode()

bytes:字节类型,通过decode()转化为str类型

bytes.decode()

requests如何发送请求和获取响应

response = requests.get(url)
response.text -> str
response.encoding="utf-8"
response.content -> bytes
response.content.decode()

发送带headers的请求

headers = {"User-Agent": "从浏览器中复制"}
requests.get(url, headers=headers)

发送带参数的请求

params = {"": ""}
url_temp = "不完整的URL地址"
requests.get(url_temp, params=params)

发送post请求

data = {"从浏览器中form data的位置寻找"}
requests.post(url, data=data)

requests中使用代理

proxies = {协议:协议 + ip + 端口}
requests.get(url, proxies=proxies)

使用代理的目的:

反反爬

隐藏真实ip

代理的分类

高匿名:不知道在使用代理

匿名:知道在使用代理,但是不知道真实ip

透明:对方知道真实的ip

session的使用

session = requests.Session()
session.post(url, data)  # cookie会存在session中
session.get(url)  # 会带上之前的cookie

列表推导式

In [41]: [i for i in range(10)]
Out[41]: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
In [42]: [i/2 for i in range(10)]
Out[42]: [0.0, 0.5, 1.0, 1.5, 2.0, 2.5, 3.0, 3.5, 4.0, 4.5]
In [43]: [i/2 for i in range(10) if i%2==0]

面向对象

对象:生活中的客观事物

类:对事物的抽象,在代码中实现class类型

实例:使用之前对类的实例化之后的记录

三元运算符的使用

if 条件成立,if前面的结果赋值给to,否则else后面的内容赋值给to

to = "en" if lan == "zh" else "zh"

requests模拟登录的两类方法

1.session实例化对象

session = requests.Session()
session.get(url)  # cookie保存在session中
session.get(url)  # 带上保存在session中cookie

2.requests进行携带cookie登录

cookie字符串放在headers中

headers = {"cookie_name": "cookie_value"}
resp = requests.get(url, headers=headers)

把cookie字典交给requests请求方法的cookies

cookies = {"cookie_name": "cookie_value"}
resp = requests.get(url, cookies=cookies)

字典推导式

In [8]: {i:i+10 for i in range(10)}
Out[8]: {0: 10, 1: 11, 2: 12, 3: 13, 4: 14, 5: 15, 6: 16, 7: 17, 8: 18, 9: 19}
In [9]: {i:i+10 for i in range(10) if i%2==0}
Out[9]: {0: 10, 2: 12, 4: 14, 6: 16, 8: 18}

寻找登录接口的方法

1.form表单action对应的url地址

用户名和密码的input标签中,name的值作为键,用户名和密码作为值的字典,作为post data

2.通过抓包,定位url地址

form data

分析js,获取加密的数据

1.观察变化

2.确定js的位置

从event listener中寻找

search all file中寻找关键字

3.进行分析

通过添加断点的方式分析js

4.执行js

完全的使用python模拟js的执行过程

requests处理ssl证书

requests.get(url, verify=False)

获取响应中的cookie,转化为字典

response = requests.get(url, headers=headers)
requests.utils.dict_from_cookiejar(response.cookies)

超时参数的使用

requests.get(url,timeout=3)

retrying模块的使用

from retrying import retry

# 通过装饰器的方式使用retry,进行异常捕获,重新执行被装饰的函数
@retry(stop_max_attempt_number=3)
def _func():
    pass

def func():
    try:
        _func()
    except Exception as e:
        print(e)

爬虫中数据的分类

结构化数据:json,xml

直接使用模块转化为python类型

非结构化数据:html

re,xpath

json是什么

数据交换格式

json模块的使用

json.loads(json_str)  # json字符串转化为python类型
json.dumps(python_type, ensure_ascii=False, indent=2)  # python类型转化为json字符串
json.load()  # 把包含json的类文件对象中的数据提取出来转化为python类型
json.dump()  # python类型转化为json格式存入类文件对象中

正则的语法

字符

`.` 匹配到出了\n之外的所有字符,re.S模式下可以匹配\n

`\` 转义

`[]` 或的效果,从中选择一个, `[abc]+` 能够匹配多个

`|` 或的效果,选择`|`两边的内容

预定义的字符集

`\d` 数字

`\s` 空白字符串,包含空格、\n,\t

`\w` 单词字符,`a-zA-Z0-9_`

数量词

`*` 匹配0次或者多次

`+` 匹配一次或者多次

`?` 能够匹配0-1次,让*,+非贪婪

re模块的常用方法

re.findall("正则表达式", "待匹配的字符串")  # 返回列表,或者是空列表
re.sub("regex", "_", "待替换的字符串")  # 返回字符串
re.compile("regex", re.S/re.DOTALL)  # 返回一个p模型
p.findall("待匹配的字符串")
p.sub("_", "待替换的字符串")

原始字符串r

定义:特殊符号原本的字面意思

用途:

正则中,能够忽略转义符号带来的影响

windows文件路径

xpath语法

`//` 的用途

`//a` 当前html页面上的所有的a

`bookstore//book` bookstore下的所有的book元素

`div//a` div中所有的a,包括div下的后代节点中的a

`a//text()` a下的所有的文本

`@` 的使用

`//a/@href` 获取所有的a标签下的href的值

`//title[@lang="eng"]` 选择lang=eng的title标签

`text()` 的使用

`//a/text()` 获取所有的a下的文本

`//a[text()='下一页']` 获取文本为下一页的a标签

`a//text()` a下的所有的文本

xpath查找特定的节点

`//a[1]` 选择第一个

`//a[last()]` 最后一个

`//a[position()<4]` 前三个

lxml模块的使用

from lxml import etree
element = etree.HTML(bytes或者str类型的字符串)  # 返回element
element.xpath("xpath字符串")  # 返回列表
etree.tostring(element)  # 返回bytes类型字符串
# 数据提取时:先分组,再提取数据

xpath的包含语法

`//a[contains(text(),"下一页")]`选择文本包含“下一页”三个字的a标签

`//a[contains(@class,'n')]` class包含n的a标签

url地址解码的方法

requests.utils.unquote(url)

准备url地址

知道url地址的规律,知道一共多少页,准备url列表,果壳,糗百

不知道url地址规律,或者不知道一共多少页,准备start_url ,贴吧

多线程中threading模块、队列的使用

t1 = threading.Thread(target=func, args=(,))
t1.setDaemon(True)  # 设置为守护线程
t1.start()  # 此时线程才会启动
from queue import Queue

q = Queue()
q.put()  # 计数+1
q.get()  # 计数不会-1
q.join()  # 让主线程阻塞,等待队列任务计数,计数为0结束
q.task_done()  # 和get一起,计数-1

多进程中进程和队列的使用

p = multiprocessing.Process(targe=func)
p.damone = True  # 设置为守护进程,主进程结束,子进程结束
p.start()
from multiprocessing import JoinableQueue

q = JoinableQueue()
q.put()  # 计数+1
q.get()  # 计数不会-1
q.join()  # 让主进程阻塞,等待队列任务计数,计数为0队列任务结束
q.task_done()  # 和get一起,计数-1

线程池和协程池的使用

from multiprocessing.dummy import Pool  # 线程池
pool = Pool(5)
pool.apply_async(func, callback=func2)
import gevent.monkey

gevent.monkey.patch_all()
from gevent.pool import Pool

pool = Pool(5)
pool.apply_async(func, callback=func2)

 

猜你喜欢

转载自blog.csdn.net/apollo_miracle/article/details/84892226