Python爬虫上手+RE+BS+XPATH

目录

一、爬虫基础

1、robots协议

2、http协议

(1)概念

(2)常用的请求头信息

(3) 常用响应头信息

3、https协议

4、加密方式

二、requests模块

1、解释

(1)requests 模块

(2)作用

(3)如何使用(request模块的编码流程)

2、第一个简单爬虫

 3、输入参数,爬取页面搜索结果

4、爬取翻译某个界面的数据

分析 xhr  可以得到

5、爬取电影排行榜信息

6、爬取城市餐厅地址

三、数据解析

1、爬取图片数据,有指定图片url

2、根据re爬取指定信息

3、爬取电影名加迅雷下载地址

4、拿到json数据

5、利用bs批量下载图片

四、xpath解析(重点)

1、前置知识

(1)入门 1

(2)入门2

2、实战


一、爬虫基础

1、robots协议

规定了网站哪些是可爬,哪些不可爬,君子协议

2、http协议

(1)概念

服务器和客户端进行数据交互的一种形式

(2)常用的请求头信息

user-agent:请求载体的身份标识

Connection :请求完毕后,是断开连接,还是保持连接

(3) 常用响应头信息

connect-type 服务器响应回客户端的数据类型

3、https协议

安全的超文本传输协议

4、加密方式

对称密钥加密

非对称密钥加密

证书密钥加密

二、requests模块

1、解释

(1)requests 模块

Python中,原生的一款基于网络请求的模块,功能非常强大,简单便捷,效率极高。

(2)作用

模拟浏览器发请求

(3)如何使用(request模块的编码流程)

-- 指定 URL

-- 发起请求

-- 获取响应数据

-- 持久化存储

2、第一个简单爬虫

"""
爬取首页数据
"""
import requests

# 需要爬取的网页url
url_real = '网址'


# 获取响应对象
def url_request(url):
    return requests.get(url)


# 持久化存储爬取的数据
def storage_request(url):
    response = url_request(url=url)
    with open('test1.html', 'w', encoding='utf-8') as f:
        f.write(response.text)
    print("爬虫结束")


# 主程序入口
if __name__ == '__main__':
    storage_request(url_real)

运行结果如下:

 3、输入参数,爬取页面搜索结果

"""
输入参数,爬取搜索的结果页面
此处我们需要伪造UA,否则爬取结果会显示:需要验证码验证

UA:User-Agent (请求载体的身份标识)
UA检测 :门户网站会检测对应请求的载体身份标识,如果检测到标识是来自某一款浏览器,说明是正常的请求,否则说明不正常(爬虫),则服务器可能会拒绝请求
UA伪装 :让爬虫对应的请求载体标识伪装成某一款浏览器

"""
import requests


# 获取响应对象
def input_somthing(kw):
    url_real = '网址'
    headers = {
        'User-Agent': 'Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/100.0.4896.88 Mobile Safari/537.36'
    }
    param = {
        'query': kw
    }
    return requests.get(url=url_real, params=param, headers=headers)


# 持久化存储爬取的数据
def storage_request(kw):
    response = input_somthing(kw)
    with open('test2.html', 'w', encoding='utf-8') as f:
        f.write(response.text)
    print("爬虫结束")


# 主程序入口
if __name__ == '__main__':
    kw = input('输入想要查询的内容:')
    storage_request(kw)

4、爬取翻译某个界面的数据

分析 xhr  可以得到

我们对 url  发起了一个  post请求,携带一个  kw值为dog

返回的是一个json

代码如下

"""
爬取翻译结果,结果为json

"""
import json

import requests


# 获取响应对象
def input_somthing(kw):
    # 需要请求的url网址
    url_real = '网址'
    # UA伪装
    headers = {
        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:100.0) Gecko/20100101 Firefox/100.0'
    }
    # post 请求的参数
    data = {
        'kw': kw
    }
    # 返回请求发送
    return requests.post(url=url_real, data=data, headers=headers)


# 持久化存储爬取的数据
def storage_request(kw):
    response = input_somthing(kw)
    job = response.json()
    # 存储
    with open('test3.json', 'w', encoding='utf-8') as f:
        # ensure_ascii 不使用ASCII码
        json.dump(job, f, indent=4,ensure_ascii=False)
    print("爬虫结束")


# 主程序入口
if __name__ == '__main__':
    kw = input('输入想要查询的内容:')
    storage_request(kw)

5、爬取电影排行榜信息

代码如下:

"""
爬取电影排行榜信息

"""
import json
import requests


# 获取响应对象
def get_response():
    # 需要请求的url网址
    url = '网址'
    # UA伪装
    headers = {
        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:100.0) Gecko/20100101 Firefox/100.0'
    }
    # get 请求的参数
    param = {
        'type': '24',
        'interval_id': '100:90',
        'action': '',
        'start': '1',  # 从库中的第几个电影去取
        'limit': '20'  # 一次取得电影的个数
    }
    # 返回请求发送
    return requests.get(url=url, params=param, headers=headers)


# 持久化存储爬取的数据
def storage_request():
    response = get_response()
    job = response.json()
    # 存储
    with open('json/test4.json', 'w', encoding='utf-8') as f:
        # ensure_ascii 不使用ASCII码
        json.dump(job, f, indent=4, ensure_ascii=False)
    print("爬虫结束")


# 主程序入口
if __name__ == '__main__':
    storage_request()

6、爬取城市餐厅地址

"""
爬取餐厅地址
"""
import json
import requests


# 获取响应对象
def post_response(kw):
    # 需要请求的url网址
    url = '网址'
    # UA伪装
    headers = {
        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:100.0) Gecko/20100101 Firefox/100.0'
    }
    # get 请求的参数
    param = {
        'cname': '',
        'pid': '',
        'keyword': kw,
        'pageIndex': '1',  # 第几页
        'pageSize': '10'  # 一页几个数据
    }
    # 返回请求发送
    return requests.post(url=url,headers=headers,params=param)


# 持久化存储爬取的数据
def storage_request(kw):
    response = post_response(kw)
    job = response.text
    new_job = json.loads(job)
    # 存储
    with open('json/test5.json', 'w', encoding='utf-8') as f:
        # ensure_ascii 不使用ASCII码
        json.dump(new_job, f, indent=4, ensure_ascii=False)
    print("爬虫结束")


# 主程序入口
if __name__ == '__main__':
    kw = input('请输入地名:')
    storage_request(kw)

三、数据解析

1、爬取图片数据,有指定图片url

"""
爬取图片数据
有指定图片url
"""
import requests


# 获取响应对象
def requ_response():
    # 需要请求的url网址
    url = '网址'
    # UA伪装
    headers = {
        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:100.0) Gecko/20100101 Firefox/100.0'
    }
    # 返回请求发送
    return requests.get(url=url, headers=headers)


# 持久化存储爬取的数据
def storage_request():
    # content 存储的是图片二进制文件
    request = requ_response().content
    # 存储
    with open('json/test7.jpg', 'wb') as f:
        f.write(request)
    print("爬虫结束")


# 主程序入口
if __name__ == '__main__':
    storage_request()

2、根据re爬取指定信息

"""
"""
import re

import requests

url = '网址'
headers = {
    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:100.0) Gecko/20100101 Firefox/100.0'
}
# 爬取页面 html 代码
get_response = requests.get(url=url, headers=headers)
page_text = get_response.text

# 解析数据
obj = re.compile(r'<li>.*?<div class="item">.*?<span class="title">'
                 r'(?P<name>.*?)</span>.*?<p class="">.*?<br>(?P<year>.*?)&nbsp'
                 r'.*?<span class="rating_num" property="v:average">(?P<score>.*?)</span>', re.S)
result = obj.finditer(page_text)
for it in result:
    print('电影名:' + it.group('name') + ';上映时间:' + it.group('year').strip() + ';电影评分:' + it.group('score').strip())
get_response.close()

3、爬取电影名加下载地址

"""
定位到2022必看热片
从2022必看热片中提取子页面的链接地址
请求子页面的链接地址,拿到我们想要的下载地址(下载地址)
"""
import re
import requests
# 爬取的网页主页面
url = '网址'

# 若是爬不到 可在request中添加,不进行安全验证 verify=False
resp = requests.get(url=url)
resp.encoding = 'gb2312'  # 乱码指定字符集
# 拿到主页面的html
page_text = resp.text
# 制定第一次正则,拿取包含电影名和子页面地址的html片段
obj = re.compile('.*2022必看热片</span>.*?<ul>(?P<a>.*?)</ul>', re.S)
result = obj.finditer(page_text)
for it in result:
    # 将拿取的html片段存储在tmp中
    tmp = it.group('a').strip()
# 制定第二次正则,拿取第一次取得html片段中包含的电影名和子页面地址
obj2 = re.compile("<li><a href='(?P<ur>.*?)' title.*?《(?P<name>.*?)》", re.S)
result2 = obj2.finditer(tmp)
for it in result2:
    # tmp = it.group('name') + '  ' + url + it.group('ur')
    # 将拿取得子页面地址片段和地址拼接形成完整的url地址
    url2 = url + it.group('ur')
    # 对子页面地址发起请求,
    res2 = requests.get(url2)
    # 乱码使用解码
    res2.encoding = 'gb2312'
    # 拿取子页面的html
    txt = res2.text
    # 制定第三次正则,拿取子页面中的迅雷下载地址
    obj3 = re.compile('【下载地址】.*?<a href="(?P<pp>magnet.*?)">magnet', re.S)
    last = obj3.finditer(txt)
    for a in last:
        # 打印出 电影名和迅雷下载地址
        print(it.group('name') + '  ' + a.group('pp'))

4、拿到json数据

"""
"""
import json

import requests

url = '网址'
headers = {
    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:100.0) Gecko/20100101 Firefox/100.0'
}
params = {
    'limit': "20",
    'current': "1",
    'pubDateStartTime': "",
    'pubDateEndTime': "",
    'prodPcatid': "",
    'prodCatid': "",
    'prodName': ""
}
job = requests.post(url=url, headers=headers, params=params)
a = job.json()
print(json.dumps(a,indent=4,ensure_ascii=False))

5、利用bs批量下载图片

"""
"""
import time

import requests
from bs4 import BeautifulSoup

url = '网址'

res = requests.get(url=url)
res.encoding = 'utf-8'
# 拿到网页源代码
page_text = res.text
# 把源代码交给bs,并说明是html代码
main_page = BeautifulSoup(page_text, 'html.parser')
# find 找一次停止   find_all 一直找到最后
alist = main_page.find('div', class_='swiper-box').find_all('a')
for a in alist:
    # 使用get命令取具体标签值
    # print(url + a.get('href'))
    new_url = url + a.get('href')
    page_text = requests.get(new_url).text
    main_page = BeautifulSoup(page_text, 'html.parser')
    img = main_page.find('section', class_='img-content').find('img')
    # print(blist.get('src'))
    # 下载图片
    # 拿到图片的字节
    img_resp = requests.get(url=img.get('src')).content
    img_name = img.get('src').split('/')[-1]
    print(img_name)
    with open('img/'+img_name, 'wb') as f:
        f.write(img_resp)
    print('1111111111111111111111')

print('over')

四、xpath解析(重点)

1、前置知识

(1)入门 1

xpath 是在XML 文档中搜索内容的一门语言

html 是 xml的一个子集

代码如下:

"""
xpath 爬取
"""
from lxml import etree

xml = """
<book>
    <id>1111</id>
    <nick>aaaaaaa</nick>
    <name>只是当时已惘然</name>
    <price>9.99</price>
    <author>
        <nick>苏轼</nick>
        <nick>柳宗元</nick>
        <div>
            <nick>王安石</nick>
            <div>
                <nick>1111</nick>
            </div>
        </div>
        <div>
            <nick>2222</nick>
        </div>
    </author>
</book>
"""
tree = etree.XML(xml)
# 表示层级关系,第一个/是根节点
result = tree.xpath('/book/name/text()')  # text() 拿文本
result2 = tree.xpath('/book/author/nick/text()')

# 加双斜杠 代表查找下所有的nick(所有后代)
result3 = tree.xpath('/book/author//nick/text()')

# * 代表通配符  任意节点
result4 = tree.xpath('/book/author/*/nick/text()')

# book下所有的nick后代
result5 = tree.xpath('/book//nick/text()')

print(result)
print(result2)
print(result3)
print(result4)
print(result5)

(2)入门2

from lxml import html

tree = html.parse('json/a.html')

# xpath 的顺序是从1 开始数数的,[] 表示索引
result = tree.xpath('/html/body/div/ol/li[1]/text()')

# 取标签中的指定值 如下
result2 = tree.xpath('/html/body/div/ul/li/a[@href="dapao"]/text()')

# 循环打印所有的  li
result3 = tree.xpath('/html/body/div/ul/li')

for li in result3:
    # 从每一个li中提取信息
    result4 = li.xpath('./a/text()')  # 在li中继续寻找
    print(result4)
    # 拿取 标签里的属性值
    result5 = li.xpath('./a/@href')
    print(result5)

# 直接打印
print(tree.xpath('/html/body/div/ol/li[1]/text()'))

2、实战

"""
利用xpath爬取相关信息
"""

import requests
from lxml import etree

url = '网址'

res = requests.get(url)
page_text = res.text

tree = etree.HTML(page_text)

divs = tree.xpath('/html/body/div[6]/div/div/div[2]/div[5]/div[1]/div')

for div in divs:
    # 价格
    price = div.xpath('./div/div/a[2]/div[2]/div[1]/span[1]/text()')[0]
    # 近半年成交数
    num = div.xpath('./div/div/a[2]/div[2]/div[1]/span[2]/text()')[0]
    # title
    title = 'python'.join(div.xpath('./div/div/a[2]/div[2]/div[2]/p/text()'))
    # 位置
    loca = div.xpath('./div/div/a[1]/div[1]/div/span/text()')[0]
    print(loca + '---' + title + '---' + price + '---' + num)

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值