python爬虫入门

1-1  主要内容

l  爬虫概述:了解什么是爬虫

l  爬虫优势:知道爬虫用在什么地方

l  爬虫实现方式:了解实现爬虫用到的各种技术

l  爬虫的分类:了解爬虫工作相关的一些(不同爬虫)区别

第一个操作程序:采集新浪社区新闻首页数据

l  爬虫请求操作:伪造请求[技术实现]

l  爬虫请求操作:模仿用户行为[社会工程学]

l  爬虫请求操作:请求隐藏[代理]

 

1-2   课程内容

1. 软件安装

python2.7开发环境

学生端程序

pycharm开发工具

虚拟环境:virtualenv

    每个项目一个独立的虚拟环境

    方便项目部署时收集开发环境中的模块:pip freeze>pkg.list

 

 

1. 什么是爬虫[爬虫概述]

 

爬虫:Spider

    爬虫-> 蚂蚁下载软件 | 迅雷下载 | ..

        小脚本程序,从网络上采集要下载的数据的资源->完成高速下载

    爬虫-> 度娘、谷哥..搜索引擎

       搜索引擎-> 采集数据的程序-> 从网络上搜索数据提供给搜索引擎使用

       百度-> 关键词-> 包含该关键词的所有网页

    公司|企业数据进行深度分析-> 数据挖掘-> 大数据-> 大量的数据处理

       大量的数据从哪里来?

 

数据的重要性

    软件:用来解决生活中的问题!

    解决生活中的问题,核心思想?

    核心:处理数据!

    操作:增删改查[CRUD]

 

数据从哪里来?

    数据:都是从生活中来的!

    生活中的数据,怎么到自己需要的地方[数据库]

   

n  手工采集:可以采集数据,但是操作效率低下

n  内部数据:公司内部数据,权限范围内尽情使用!:数据有限、较强的针对性

n  数据交易:数据采集迅速、费用较高;-- 数据不能定制化!

爬虫采集:定向数据采集;成本较高、数据定制化很强、数据针对性很强

u  搜索引擎:不是我们的重点!

u  定向爬虫:我们工作的重点!-- 开启了保护和反保护的斗争

u  爬虫[采集数据]和反爬虫[防止恶意采集数据]

 

2. 爬虫的采集方式——分类

通用爬虫:一般用在搜索引擎中:针对所有数据进行广泛采集[广度]

    搜索引擎作为爬虫~必须遵守爬虫采集数据的约定协议

    民间组织约定的爬虫采集数据协议:ROBOT协议

    爬虫:好的一面~可以将自己的网站让更多的人通过搜索引擎访问~网络流量分流

    ROBOT协议:是一种约定的规范;针对通用爬虫进行的数据采集限制

 

 

聚焦爬虫:也成为定向爬虫,针对目标数据进行定向数据采集[深度]

    每个数据采集任务,都可能要开发一套新的项目 :程序开发密集度

数据采集定向采集[在不违反中华人民共和国宪法的前提下]可以针对任何数据进行采集(一般正规的公司安排的数据采集任务基本都是合法的->公司承担责任):数据定向性

    技能要求:上手快,入门简单,对数据的分析要求较高!

    工作的重点:聚焦爬虫;工作的核心:采集数据;

 

 

PS:爬虫~是通过程序的方式,自动采集数据;程序操作比自然人的操作效率高出很多很多倍;所以如果一旦通过无限制的爬虫对网站发起请求,[爬虫的频繁请求让服务器资源迅速消耗,最终导致服务器内存不存或者其他后果!],网站很容易DDOS

DDOS[拒绝服务攻击]

 

3. 关于历史数据的处理

 

百度搜索-> 爬虫采集了网络中的大部分网站的数据-> 其他人通过搜索网站,可以直接在搜索页面中进入指定的网站

    PS:某个网站进行了更新,百度以前搜索到的页面数据变化了!数据不一致~

    百度爬虫对原来采集过的数据要实时进行更新

增量爬虫:需要实时对历史采集数据进行更新[历史数据会发生变化]

 

股票数据采集-> 采集了过去10年每一个交易日的股票历史数据,方便对未来的数据进行分析处理

    PS:需要对历史数据进行更新吗?

累积爬虫:历史数据不会发生变化,一旦数据执行完成,数据就是固定的

 

 

程序开发:第一个爬虫程序

开发环境:python2.7

开发工具:pycharm

 

python2和python3区别

编码:Python2使用的是ascii编码;python3使用的是unicode编码

    UTF-8-> unicode trasfer format 8bit 主持中文

    ascii-> 不支持中文 -> ANSI->扩展ANSI->..

 

表示英文->1个字符->2个字节->16位

表示汉字->2个字符->4个字节->32位->国家标准编码GB2312->GBK->GB18030

 

英文-中文,编码方式可能不同,就会造成乱码的问题!

解决乱码的问题-> 不论什么字符->转换成字节->按照指定的编码转换成字符

 

 

开始开发:

    python2使用的是ascii编码,所以源代码文件都不支持中文

    源代码代码中第一行的位置,添加支持中文的注释

    #-*- coding:utf-8 -*-

    #coding:utf-8

    #..

 

    为什么要使用python2

    python主要的版本1.x,2.x,3.x

    目前web市场主流版本:3.x[网站开发-文本字符数据的交互,配合二进制文件的处理,更多的会使用到的比较通用的unicode字符]

    爬虫工作主流版本:2.x[都是从网络上采集数据,采集的数据文本数据、二进制数据,为了方便并且统一的进行采集数据的处理,使用python2操作更加灵活]Python2在爬虫方向支持的第三方模块更多!

 

程序开发

 

 

采集到新浪网网页数据

有用?采集首页中各个模块的链接地址和名称,方便进行该模块二次数据采集

没用?其他数据~不需要

 

采集网页的源代码,为什么要用爬虫程序?鼠标右键查看源代码可以完成!

为什么要用爬虫{爬虫的优势?!}

有那么多的工具[迅雷、旋风、百度云、整站下载工具等等],为什么要用爬虫!

 

[刘文超]

[刘锐红]

最近上映了妇联3->要看这部电影,怎么办?--下载工具

最近要看一本小说->[阴阳师]-> 怎么办?--搜索引擎-搜索资源-下载工具

要获取某个网站上的大部分电商商品[名称、价格、描述]->怎么办-爬虫程序自动采集

要获取多个新闻网站上,最近1个月的所有新闻数据[标题、发布时间、编辑人、内容]->怎么办——爬虫程序自动采集

 

 

爬虫程序—发送请求给服务器,获取服务器的数据

 

爬虫程序~发送的请求什么样的?Spider Request

浏览器程序~发送的请求什么样的?Browser Request

 

这两个请求,有什么区别?

了解清楚有什么区别~才能掌握好爬虫程序的请求[伪装浏览器请求]

 

(1)    抓包工具

网络上流行的抓包工具有很多,wareshark、burpsuits、fiddler、F12窗口

 

浏览器发送的请求:F12窗口,直接查看请求信息

 

程序发送的请求:怎么看PYTHON爬虫程序发起请求的信息

 

了解请求程序发送请求和浏览器发送请求的区别:才能更加完美的伪造请求

 

(2)    请求伪造

请求对象:获取一个请求对象,通过请求对象设置用户代理[User-agent]请求头

    请求头中的K=V数据:K键值~单词首字母必须大写

 

请求对象:urllib2.Request对象

通过对urllib2.Request对象的设置,完成请求的伪造操作

 

 

 

隐藏用户:使用代理IP进行请求操作

正向代理:代理客户端发起请求,向服务器请求数据;隐藏客户端信息

 

反向代理:代理的服务端;隐藏真实服务器信息

 

都有什么样的代理:免费代理、收费代理 -- [透明代理|匿名代理|高匿代理]

 

python爬虫中,怎么使用这些代理

默认情况下,urllib2爬虫程序直接通过urlopen()发送请求!

è 查询对应的资料[官网资料|总结的资料|国外资料]

è 查看底层代码,模仿还原

 

 

采集:百度图片~美女图片

 

 

 

1. 爬虫的理论知识

a)  什么是爬虫?

b)  爬虫的分类

       i.     通用爬虫 VS 聚焦爬虫

      ii.     累积爬虫 VS 增量爬虫

c)  爬虫的实现

       i.     Java|Python|PHP|C++|C#|Ruby|Delphi|..

      ii.     python:更加专业

    iii.     urllib2基础->requests->scrapy->分布式

2. 爬虫的操作

a)  urllib2底层数据采集urlopen()函数

b)  伪造请求:伪装浏览器请求

       i.     请求对象:请求头数据、请求体数据、请求方式..

      ii.     请求头中的User-agent设置,完成浏览器请求的伪装

    iii.     请求对象:urllib2.Reuqest对象

c)  模仿用户行为:只有在特殊的情况下才会使用

       i.     随机休眠严重影响爬虫采集数据的效率

d)  隐藏客户端:使用IP代理,代理真实客户端完成对服务器数据的访问

       i.     免费代理|收费代理

      ii.     正向代理[代购]|反向代理[代理商]

    iii.     urlopen底层操作

1.  操作对象:urllib2.ProxyHandler({..})

2.  开锁对象:urllib2.build_opener(handler)

3.  发送请求:res = opener.open(url)


'''
url:https://image.baidu.com/search/acjson?tn=resultjson_com&ipn=rj&ct=201326592&is=&fp=result&queryWord=%E7%BE%8E%E5%A5%B3&cl=2&lm=-1&ie=utf-8&oe=utf-8&adpicid=&st=-1&z=&ic=0&word=%E7%BE%8E%E5%A5%B3&s=&se=&tab=&width=&height=&face=0&istype=2&qc=&nc=1&fr=&cg=girl&pn=240&rn=30&gsm=f0&1527500554991=
pn = 0   表示从第几个开始
rn =   表示往后显示多少个,最大数位:60

图片url :"thumbURL":https://ss0.bdstatic.com/70cFuHSh_Q1YnxGkpoWK1HF6hhy/it/u=983383169,2627637251&fm=27&gp=0.jpg

正则:r'https:\/\/([a-z0-9]+\.)+([a-z]+\.)+([a-z]+\/)+([a-zA-Z0-9]+\/)+([a-z]+\/)+(u=[0-9]{10},[0-9]{10})(&fm=27&gp=0)\.jpg$'
reg = re.compile('"thumbURL": "(https.*?jpg)"', )


'''

import time, random
from urllib2 import Request, ProxyHandler, build_opener, urlopen
import re

#定义请求的url
base_url = "https://image.baidu.com/search/acjson?tn=resultjson_com&ipn=rj&ct=201326592&is=&fp=result&queryWord=%E7%BE%8E%E5%A5%B3&cl=2&lm=-1&ie=utf-8&oe=utf-8&adpicid=&st=-1&z=&ic=0&word=%E7%BE%8E%E5%A5%B3&s=&se=&tab=&width=&height=&face=0&istype=2&qc=&nc=1&fr=&cg=girl&pn={}&rn=60&gsm=f0&"+str(int(time.time()*1000))+"="
# 定义User-ahent

base_url_list = [base_url.format(n) for n in range(0,360,60)]
useragent = [
    'Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; Trident/5.0;',
    'Mozilla/5.0 (Windows NT 6.1; rv:2.0.1) Gecko/20100101 Firefox/4.0.1',
    'Opera/9.80 (Windows NT 6.1; U; en) Presto/2.8.131 Version/11.11',
]

for index,next_url in enumerate(base_url_list):
    # 定义请求头
    headers = {
        # 'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8',
        # 'Accept-Encoding': 'gzip, deflate, br',
        # 'Accept-Language': 'zh-CN,zh;q=0.9',
        # 'Cache-Control': 'max-age=0',
        # 'Connection': 'keep-alive',
        'Cookie': 'BDqhfp=%E7%BE%8E%E5%A5%B3%26%260-10-1undefined%26%260%26%261; BAIDUID=0F629939E752EC3B893185C15F35C5C8:FG=1; BIDUPSID=0F629939E752EC3B893185C15F35C5C8; PSTM=1527488835; BDRCVFR[7JA7KA5iDWT]=mk3SLVN4HKm; H_PS_PSSID=; BDORZ=FFFB88E999055A3F8A630C64834BD6D0; PSINO=5; BDRCVFR[dG2JNJb_ajR]=mk3SLVN4HKm; BDRCVFR[X_XKQks0S63]=mk3SLVN4HKm; firstShowTip=1; indexPageSugList=%5B%22%E7%BE%8E%E5%A5%B3%22%5D; cleanHistoryStatus=0',
        'Host': 'image.baidu.com',
        # 'Upgrade-Insecure-Requests': '1',
        'User-agent': random.choice(useragent)
    }

    # print headers
    # 构建请求对象
    request =  Request(base_url,headers = headers)
    # 自定义代理操作对象
    proxy_handler = ProxyHandler({'http':'60.176.232.13:6666'})
    # 构建一个opener对象
    proxy_opener = build_opener(proxy_handler)
    # 使用自定义opener访问服务器数据,得到相应
    response = proxy_opener.open(request)
    response = urlopen(request)
    content =  response.read()
    # print content
    # 通过正则匹配图片url地址
    print('>>>>>>>>>>>>>>>获取%d页图片url'%index)
    ret_list = re.findall('"thumbURL":"(https.*?jpg)"',content)
    print ('获取第%d页的图片'%index)
    for num,ret in enumerate(ret_list):
        headers = {
                        # 'Accept': 'text/html, application/xhtml+xml, application/xml;q = 0.9, image/webp, image/apng, */*;q = 0.8',
                       # 'Accept - Encoding': 'gzip,deflate,br',
                       # 'Accept - Language': 'zh - CN, zh;q = 0.9',
                       # 'Cache - Control': 'max - age = 0'
                       # 'Connection': 'keep - alive',
                        'Host': 'ss1.bdstatic.com',
                        'If - Modified - Since': 'Thu, 01 Jan 1970 00:00:00 GMT',
                        'If - None - Match': '8bbc885d21ace8283d7f41cf778c8fb3',
                        'Upgrade - Insecure - Requests': '1',
                        'User - Agent':random.choice(useragent),
        }
        request = Request(ret, headers=headers)
        # 自定义代理操作对象
        proxy_handler = ProxyHandler({'http': '60.176.232.13:6666'})
        # 构建一个opener对象
        proxy_opener = build_opener(proxy_handler)
        # 使用自定义opener访问服务器数据,得到相应j
        response = proxy_opener.open(request)
        response = urlopen(request)
        print('>>>>>>>>>>>开始保存图片' + str(index)+'-'+str(num))
        with open( './images/'+str(index)+'-'+str(num)+".jpg", "wb") as f:
            f.write(response.read())

 

你可能感兴趣的:(python爬虫入门)