python爬虫实战


->网课

一.基础

robots.txt

如https://www.taobao.com/robots.txt

查看淘宝能爬取的内容

常用请求头信息

User-Agent::请求载体的身份标识
Connection:请求完毕后,是断开连接还是保持连接

常用响应头信息

Content-Type:服务器响应回客户端的数据类型

https协议

—安全的http协议(超文本传输协议)

加密方式

对称秘钥加密

客户端常用!有风险!
在这里插入图片描述

非对称秘钥加密

对称秘钥加密的升级
在这里插入图片描述

证书秘钥加密------https采用的

在这里插入图片描述
在这里插入图片描述

阿贾克斯是什么

阿贾克斯是什么,怎么创建和优点

二.ruquests模块

urllib模块复杂,ruquests模块:方便!

1.作用:

模拟浏览器发请求

2.如何使用:

1.指定url
URL就是你的IE地址栏上的那串字符
2.-发起请求
3.获取响应数据
4.持久化存储

3.环境安装

pycharm

 pip install requests

anacnda不用安装

4.实战

爬取搜狗首页的数据

coding=utf-8的作用

在这里插入图片描述

爬取网页源代码

import requests
if __name__ == "__main__":
    # 指定url
    url = 'https://hao.360.com/'
    # 发起请求
    # get方法会返回一个响应对象
    response = requests.get(url=url)
    # 获取相应数据,text返回 的是字符串形式的响应数据
    page_text = response.text
    print(page_text)
    # 持久化储存
    with open('./sougou.html','w',encoding='utf-8') as fp:
        fp.write(page_text)
    print('爬取数据结束!!!')

爬取sogou词条

UA检测

在这里插入图片描述

UA伪装

将对应的User-Agent封装到一个字典中

import requests
if __name__ == "__main__":
    headers = {
        'User-Agent':'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36'
        }
    url = 'https://www.sogou.com/web'
    #将参数封装的字典中
    kw = input('enter a word')
    param = {
        'query':kw
        }
    #对指定url发起请求是携带参数的
    response = requests.get(url=url,params=param,headers=headers)
    page_text = response.text
    fileName = kw+'.html'
    with open(fileName,'w',encoding='utf-8') as fp:
        fp.write(page_text)
    print(fileName,'保存成功!!!')

破解百度翻译

交互数据包—post请求—携带了参数

在这里插入图片描述
在这里插入图片描述

响应数据是一组json数据

在这里插入图片描述

爬取sogou词条

import requests
if __name__ == "__main__":
    headers = {
        'User-Agent':'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36'
        }
    url = 'https://www.sogou.com/web'
    #将参数封装的字典中
    kw = input('enter a word')
    param = {
        'query':kw     #默认是字符串
        }
    #对指定url发起请求是携带参数的
    response = requests.get(url=url,params=param,headers=headers)
    page_text = response.text
    fileName = kw+'.html'
    with open(fileName,'w',encoding='utf-8') as fp:
        fp.write(page_text)
    print(fileName,'保存成功!!!')

爬取豆瓣

import requests
import json
if __name__ == "__main__":
    url = 'https://movie.douban.com/j/chart/top_list'
    param = {
        'type' : '24',
        'interval_id' : '100:90',
        'action' : '',
        'start' : '0',#从库中的第几部电影去取
        'limit' : '20',#一次取出的个数
        }
    headers = {
        'User-Agent' : 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36'
        }
    response = requests.get(url=url,params=param,headers=headers)
    list_date = response.json()
    fp = open('./douban.json','w',encoding='utf-8')
    json.dump(list_date,fp=fp,ensure_ascii=False)
    print('over!!!')

爬取KFC位置

import requests

url = 'http://www.kfc.com.cn/kfccda/ashx/GetStoreList.ashx?op=keyword'
key = input('请输入名称:')
date = {
        'MIME类型': 'application/x-www-form-urlencoded; charset=UTF-8',
        'cname':'',
        'pid':'',
        'keyword':key,#默认是字符串
        'pageIndex':'1',
        'pageSize':'10'
        }
headers = {
        'User-Agent':'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36'
        }
response = requests.post(url=url,data=date,headers=headers)
page_text = response.text
with open(key+'.text',mode='w',encoding='utf-8') as fp:
    fp.write(page_text)
print('保存成功!!!')

如果结果是-1000,则说明是url错误

爬取化妆品生产许可平台

化妆品生产许可平台

检测各公司是否是由ajax对应的请求

1.代码

import requests
if __name__ == "__main__":
    url = 'http://scxk.nmpa.gov.cn:81/xk/'
    headers = {
        'User-Agent':'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36'
        }
    page_text = requests.get(url=url,headers=headers).text
    with open('./化妆品.html','w',encoding='utf-8') as fp:
        fp.write(page_text)

html打开如下

在这里插入图片描述

2.抓包工具

在这里插入图片描述

按ctrl f 搜索

在这里插入图片描述

0 of 0 表示没搜到

在这里插入图片描述json在线解析
在这里插入图片描述

证明猜想成立

数据解析

在这里插入图片描述

聚焦爬虫

->爬取页面中指定的页面内容.
通用->聚焦

数据解析分类

-正则

在这里插入图片描述

爬取囧图

囧图百科

# -*- coding: utf-8 -*-
"""
Created on Mon Mar 29 19:35:56 2021

@author: ASUS
"""

import requests
import re
import os

if __name__ == "__main__":
    if not os.path.exists('./囧图图片'):
        os.mkdir('./囧图图片')
    headers = {
        'User-Agent':'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36'
        }    
    #创建一个文件夹,保存所有的图片
    
    #ex = '<img src="(.*?)" alt="(.*?)" width=.*? height=.*?>'错误
    #通用模板
    url = 'https://www.qiushibaike.com/imgrank/page/%d/'
    for pageNum in range(1,3):#页码控制
        new_url = format(url%pageNum)
        page_text = requests.get(url=new_url,headers=headers).text
        ex = '<div class="thumb">.*?<img src="(.*?)" alt.*?</div>'
        img_src_list = re.findall(ex,page_text,re.S)#re.S单行匹配#.M多行匹配
        #print(img_src_list)
        for src in img_src_list:
            #拼接出一个完成的图片url
            src = 'https:'+src
            #请求到了图片的二进制数据
            img_data = requests.get(url=src,headers=headers).content
            #生成图片名称
            img_name = src.split('/')[-1]
            #图片储存的路径
            imgPath = './囧事图片'+img_name
            with open(imgPath,'wb') as fp:
                fp.write(img_data)
                print(img_name,'下载成功!!!')   

bs4

讲解代码
from bs4 import BeautifulSoup
if __name__ == "__main__":
    #将本地的html文档中的数据加载到该对象中
    fp = open('./text.html','r',encoding='utf-8')
    soup = BeautifulSoup(fp,'lxml')
    # print(soup)
    # tagName标签名
    # print(soup.a)# soup.tagName返回的是html中第一次返回的a标签
    # print(soup.div)
    # find('tagName')等同于soup.div
    # print(soup.find('div'))#print(soup.div)
    # print(soup.find('div',class = 'song'))
    # print(soup.find_all('a'))
    print(soup.select('.left')[0].string)
案例代码:爬三国演义
import requests
from bs4 import BeautifulSoup
#需求:爬取三国演义的章节标题
if __name__ == "__main__":
    #对首页的页面数据进行爬取
    url = 'https://www.shicimingju.com/book/sanguoyanyi.html'
    headers = {
        'User-Agent':'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36'
        }
    page_text = requests.get(url=url,headers=headers).text
    # 在首页中解析出章节的标题和详情也的url
    # 1.实例化一个对象
    soup = BeautifulSoup(page_text,'lxml')
    # 解析章节标题和详情页的url
    li_list = soup.select('.book-mulu > ul > li')
    fp = open('./三国.txt','w',encoding='utf-8')
    for li in li_list:
        title = li.a.string
        detail_url = 'https://www.shicimingju.com'+ li.a['href']
        #对详情也发起请求,解析出出章节内容
        detail_page_text = requests.get(url=detail_url,headers=headers).text
        # 解析出详情页中相关的章节内容
        detail_soup = BeautifulSoup(detail_page_text,'lxml')
        detail_soup.find('div',class_='chapter_content')
        # 解析到了章节的内容
        content = div_tag.text
        fp.write(title+':'+content+'\n')
        print(title,'爬取成功!!!')
数据解析的原理

** 1.标签定位**
** 2.提取标签、标签属性中的储存的数据值**

bs4数据解析的原理:

-1.实例化一个BeautSoup对象,并且将页面源码数据加载到该对象中
-2.通过调用BeautSoup对象中相关的属性或者方法进行标签定位和数据提取

环境安装
  • pip install bs4
  • pip install lxml
如何实例化BeautifulSoup对象:
  • 1
    from bs4 import BeautifulSoup
    
  • 2.对象的实例化:
    • 1.将本地的html文档中的数据加载到该对象中
          fp = open('./text.html','r',encoding='utf-8')
          soup = BeautifulSoup(fp,'lxml')
      
    • 2.将互联网上获取的页面源代码加载到该对象中
      page_text = response.text
      soup = BeautifulSoup(page_text,'lxml')
      
  • 3.提供的用于数据解析的方法和属性
    • soup.tagName:返回的是文档中第一次出现的a标签
    • soup.find(‘tagName’)等同于soup.div
    • 属性定位
      • soup.find(‘div’,class/id/attr = ‘song’)
  • 4.soup.find_all() :返回符合要求的所有标签(列表)(也可属性定位)
  • 5.select:
    • select(‘某种选择器(id,class,标签…选择器)’)返回的是一个列表
      • soup.select(’.tang > ul >li >a’)[0]:>表示的是一个层级
      • soup.select(’.tang > ul a’)[0]:空格表示的是多个层级
        在这里插入图片描述
        在这里插入图片描述
  • 获取标签之间文本数据
    • soup.a.text/string/get_text()
    • text/get_text():可以获取某个标签中所有的文本内容
    • string:只能获取该标签下面直系的文本内容
      get_text()是个方法
  • 获取标签中属性值
    • soup.a[‘href’]

xpath解析:通用性强

最常用且最便捷高效的一种解析方式

讲解代码
from lxml import etree
if __name__ == "__main__":
    # 实例化
    # tree = etree.parse('text.html',etree.HTMLParser())
    tree = etree.parse('text.html',etree.HTMLParser())
    # r = tree.xpath('/html/body/div')
    # r = tree.xpath('html//div')
    # r = tree.xpath('//div')
    # r = tree.xpath('//div[@class="left"]/a/text()')得到的是字符串---【“ ”】形式的,
    
    # r = tree.xpath('//div[@class="left"]/a/text()')[0]----得到文本内容
    r = tree.xpath('//div[@class="right"]//img/@src')
    print(r)
  • xpath解析原理:
    • 1.化一个etree的对象,且需要将被解析的页面源代码数据加载到该对象中
    • 2.调用etree对象中的xpath方法结合着xpath表达式实现标签的定位和内容的捕获
    • 3.环境安装:pip install lxml
    • 如何实例化一个etree对象
      • 1.将本地的html文档中的源码数据加载到etree对象中:
        etree.parse(filePath)
        
      • 2.可以将从互联网上获取的源代码加载到该对象中
        etree.HTML('page_text')
        
      • 3.xpath('xpath表达式‘)
        • /:表示的是从根节点开始定位。表示的是一个层级。
        • //:表示的是多个层级,可以从任意位置开始定位
        • 属性定位:r = tree.xpath(’//div[@class=“left”]’)----tag[@attrName=“attrValue”]
        • 索引定位:r = tree.xpath(’//div[@class=“left”]/p[3] 索引是从1开始的。
        • 取文本:r = tree.xpath(’//div[@class=“left”]/a/text()’)[0]
          • /text() 获取的是标签中直系的文本内容
          • //text() 标签中非直系的文本内容(所有的文本内容)
        • 取属性:/@attrName ==>img/src
爬取美女图片
import requests
from lxml import etree
import os
if __name__ == "__main__":
    url = 'https://pic.netbian.com/4kmeinv/'
    headers = {
        'User-Agent':'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36'
        }
    response = requests.get(url=url,headers=headers)
    # 手动设置响应数据的编码格式
    # response.encoding = 'utf-8' 
    page_text = response.text
    tree = etree.HTML(page_text)
    li_list = tree.xpath('//div[@class="slist"]/ul/li')
    
    #创建一个文件夹
    if not os.path.exists('./picLibs'):
        os.mkdir('./picLibs')
    for li in li_list:
        img_src = 'https://pic.netbian.com/' + li.xpath('./a/img/@src')[0]
        img_name = li.xpath('./a/img/@alt')[0]+'.jpg'
        #通用解决中文乱码的解决方案
        img_name = img_name.encode('iso-8859-1').decode('gbk')
        # print(img_name,img_src)
        # 请求图片进行持久化储存
        img_date = requests.get(url=img_src,headers=headers).content# 二进制
        img_path = 'picLibs/'+img_name
        with open(img_path,'wb') as fp:
            fp.write(img_date)
            print(img_name,'下载成功!!!')
爬取全国城市名
# import requests
# from lxml import etree
# if __name__ == "__main__":
#    headers = {
#        'user-agent':'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36'
#        }
   # url = 'https://www.aqistudy.cn/historydata/'
    #page_text = requests.get(url=url,headers=headers).text
    #tree = etree.HTML(page_text)
    #hot_li_list = tree.xpath('//div[@class="bottom"]/ul/li')
    #all_city_names = []
    #解析到热门城市
    #for li in hot_li_list:
     #   hot_city_name = li.xpath('./a/text()')[0]
      #  all_city_names.append(hot_city_name)
    #city_names_list = tree.xpath('//div[@class="bottom"]/ul/div[2]/li')
    #for li in city_names_list:
     #   city_name = li.xpath('./a/text()')[0]
      #  all_city_names.append(city_name)
    #print(all_city_names,len(all_city_names))
    
    
import requests
from lxml import etree
if __name__ == "__main__":
    headers = {
        'user-agent':'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36'
        }
    url = 'https://www.aqistudy.cn/historydata/'
    page_text = requests.get(url=url,headers=headers).text
    tree = etree.HTML(page_text)
    #('//div[@class="bottom"]/ul/li')
    #('//div[@class="bottom"]/ul/div[2]/li/a')
    a_list = tree.xpath('//div[@class="bottom"]/ul/li/a | //div[@class="bottom"]/ul/div[2]/li/a')
    all_city_names = []
    for a in a_list:
        city_name = a.xpath('./text()')[0]
        all_city_names.append(city_name)
    print(all_city_names,len(all_city_names))

我用的 html 文件

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>这是一个低仿的QQ注册界面</title>
  <style>
    body,div,dl,dt,dd,ul,ol,li,h1,h2,h3,h4,h5,h6,pre,code,form,fieldset,legend,input,textarea,p,blockquote,th,td
     {
       margin:0;padding:0
     }
    html{
      font-family: -apple-system,"Helvetica Neue",Arial,"PingFang SC","Hiragino Sans GB",STHeiti,"Microsoft YaHei","Microsoft JhengHei","Source Han Sans SC","Noto Sans CJK SC","Source Han Sans CN","Noto Sans SC","Source Han Sans TC","Noto Sans CJK TC","WenQuanYi Micro Hei",SimSun,sans-serif;
    }
   .left{
     width: 480px;
     height: 1000px;
     float: left;
     box-sizing: border-box;
     background-image: url("https://cdn-go.cn/qq-web/zc.qq.com/latest/v3/img/01-1.jpg");
     position: fixed;
   }
    .right{
      width: 1039px;
      height: 1000px;
      /*background-color: skyblue;*/
      float: right;
      box-sizing: border-box;
    }


    .lianghao img{
      float: left;
      margin-bottom: 2px;
    }

    .right .top .lianghao div{
      float:left;
      border-radius: 6px;
      width: 80px;
      height: 25px;
      line-height: 25x;
      font-size: 16px;
     /* margin: 0 10px 0 24px;
      padding: 0 10px 0 24px;*/
      margin: 10px 2px 0 0;
      padding: 0 5px 0 0;
      color: #fff;
      font-weight: 300;
      background: linear-gradient(126deg,#fc4754,#ff794c) #f54444;;
      text-align: right;
      box-sizing: border-box;
    }
    .top {
      /*background-color: mediumslateblue;*/
      width: 450px;
      height: 100px;
       float: right;
      box-sizing: border-box;

    }
    .lianghao{
      width: 150px;
      height: 50px;
      /*background-color: gold;*/
      float: left;
      margin-right: 40px;
      margin-top: 12px;
    }
    .language{
      width: 100px;
      height: 50px;
      /*background-color: blue;*/
      float: left;
      box-sizing: border-box;
      margin-top: 21px;
    }

    .feedback{
        width: 80px;
        height: 40px;
        float: right;
        /*background-color:greenyellow;*/
        box-sizing: border-box;
        margin-top: 12px;
        margin-right: 30px;
        line-height: 40px;
      }
  /*  .language select{
      border: transparent;
      height: 40px;
      color: #000000;
      font-size: 16px;

    }*/

    .feedback a{
      color: #cccccc;
      font-size: 16px;
      text-decoration: none;
    }
    .bottom{
      width: 520px;
      height: 600px;

      position: absolute;
      left: 50%;
      top: 35%;

    }
    .bottom .logo{
      width: 520px;
      height: 120px;
      /*background-color: orange;*/
      font-weight: 300px;
    }
    .bottom .logo .big{
      font-size: 40px;
    }
    .bottom .logo .small{
      font-size: 25px;
    }
    .logo a{
      font-size: 25px;
      text-decoration: none;
      color: #3b78dd;
      float: right;
    }
    .line{
      width: 520px;
      height: 250px;
      margin-top: 50px;

    }
    .line .name{
      border: 1px solid skyblue;
      width: 520px;
      height: 50px;
      border-radius: 6px;
    }
    .line .psd{
      border: 1px solid skyblue;
      width: 520px;
      height: 50px;
      border-radius: 6px;

    }
    .line .phone{
      border: 1px solid skyblue;
      width: 340px;
      height: 50px;
      float: right;
      border-radius: 6px;

    }
    .line select{
      border: 1px solid skyblue;
      width:150px;
      height: 52px;
      border-radius: 6px;
    }
    .re_button{
      width: 520px;
      height: 60px;
      background-color: #3b78dd;
      font-size: 22px;
      color: white;
      border-radius: 6px;

    }
    .button{
      width: 520px;
      height: 100px;

      margin-top: 30px;
    }
    #xieyi{
      color: #adadad;
      font-size: 15px;
    }
    .footer{
      width: 400px;
      height: 50px;


      box-sizing: border-box;
      margin-top: 900px;
      margin-left: 380px;
    }

    .line input{
      font-size: 20px;
      color: #adadad;
    }
    .left a{
      background: url("https://qq-web.cdn-go.cn/zc.qq.com/1c037ba1/v3/img/logo.png") no-repeat;
      background-size: 36px 43px;
      height: 43px;
      line-height: 43px;
      padding-left: 46px;
      margin-left: 30px;
      margin-top: 18px;
      font-size: 36px;
      display: block;
      color: #000000;
      text-decoration: none;
    }

    .nav {
      width: 100px;
      height: 30px;
      float: left;
      box-sizing: border-box;
      margin-top: 21px;

    }
    .nav ul li {
      float: left;
      list-style-type: none;
      width: 80px;
      /*margin-bottom: 15px;*/
    }
    .nav ul li a {
      color: #cccccc;
      text-decoration: none;
      display: block;
    }
    .nav ul li a:link{
      color: #cccccc;
      opacity: 5;
    }
    .nav ul li a:hover {
      color: #000000;
    }
    .nav li {
      line-height: 30px;
      text-align: center;
    }
    .nav ul li span{
      display: none;
      text-decoration: none;
      position: absolute;
      width: 80px;
    }
    .nav span ul li a{
      color: #cccccc;
    }
    .nav ul li:hover span {
      display: block;
      text-decoration: none;
    }
    .feedback a:hover{
      color: #000000;
    }
  </style>
</head>
<body>
  <div class="left">
    <a href="https://ssl.zc.qq.com/v3/index-chs.html?type=0" class="leftlogo">QQ</a>
  </div>
  <div class="right">
    <div class="top">
      <div class="lianghao">
        <a href="https://haoma.qq.com/shop.html#from=zc" target="_blank">
          <img src="images/qqlogo1.webp" srcset="images/qqlogo1.webp 2x"><div>QQ靓号</div>
        </a>
      </div>
      <div class="nav">
        <div id="sunav">
          <ul>
            <li class="sunav"><a href="#">简体中文</a>
              <span>
                <ul>
                    <li><a href="#">繁体中文</a></li>
                    <li><a href="#">English</a></li>
                </ul>
                </span>
            </li>
          </ul>
        </div>
        <img src="https://qq-web.cdn-go.cn/zc.qq.com/1c037ba1/v3/img/down.png" alt="">
      </div>


      <div class="feedback">
        <a href="https://support.qq.com/products/14802">意见反馈</a>
      </div>

  </div>
    <div class="bottom">
      <div class="logo">
        <span class="big">欢迎注册QQ</span> <br><br><br>
        <span class="small">每一天,乐享沟通。</span>
        <a href="https://ssl.zc.qq.com/v3/index-chs.html?type=3" target="_self">免费靓号</a>
      </div>
      <div class="line">
        <input type="text" placeholder="昵称" class="name" ><br><br><br>
        <input type="password" placeholder="密码" class="psd"><br><br><br>
        <select name="" id="" >
          <option value="">中国 +86</option>
          <option value="">中国香港特别行政区 +852</option>
          <option value="">中国澳门特别行政区 +853</option>
          <option value="">中国台湾地区 +886</option>
          <option value="">阿尔巴尼亚 +355</option>
        </select>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
        <input type="text" placeholder="手机号码" class="phone">
      </div>
      <div class="button">
        <input type="button" value="立即注册" class="re_button"><br><br>
        <input type="checkbox" >&nbsp;<span id="xieyi">我已阅读并同意相关服务条款和隐私政策</span> <img src="https://qq-web.cdn-go.cn/zc.qq.com/1c037ba1/v3/img/down.png" alt="">
      </div>
    </div>
    <div class="footer">
      Copyright © 1998-2021Tencent All Rights Reserved
    </div>
  </div>
</body>

</html>
  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值