数据清洗与数据挖掘复习笔记2

第二章 web相关技术

HTML语言规范

超文本标记语言

超文本:使用超链接的方法,把文字和图片信息相互链接,形成具有相关信息的体系。页面内可以包含图片、链接、音乐、视频、程序等非文字元素;

标记语言:在文档内使用标记标签来定义页面内容的语言

超文本标记语言:在文档内使用标记标签来定义页面内容多语言;使用标签来描述网页,适用于创建网页的标记语言,不是一种编程语言。

HTML的最初构想是作为一种交换科学和其他技术文档的一种语言,共那些不熟悉书写文档的专家使用。HTML规定一小套结构语义标签,食欲书写相对简单的文档,从而解决了标准通用标记语言复杂性的问题。除了简化了文档结构外,HTML还加入了对超文本的支持,还增加了媒体功能。

网页文件的扩展名为.html或.htm。一个网页对应着一个或者多个HTML文档,web浏览器读取HTML文档后将其以网页的形式显示。

HTML文档整体结构

标记标签

是组成HTML页面的基本内容,由尖括号包括关键词,关键词可以忽略大小写。标签属性作用下,文档可以改变样式、实现插入图片、链接、表格等。

标签的种类

闭合标签

是指开始标签和结束标签组成的一对标签,带斜杠的元素表示结束。例如<body>,</body>,这种标签允许嵌套和承载内容。

元素:从开始标签到闭合标签之间的代码为元素。

块级标签

单独占一行的标签,并且标签间的元素能够随时摄者宽度、高度、顶部和底部边距等。

例如p、h1、div、ul

空标签

没有内容的标签通常用来占位,在开始标签中自动闭合,

例如br,link,meta

行内(内嵌)标签

行内标签间的元素和其他元素在同一行上,二元素的宽度、高度、顶部和底部的边距不可设置

例如span、a、label

行内-块级标签

多个行内-块级标签的元素可以显示在同一行,可以设置宽度、高度、顶部和底部边距等

例如input、img

HTML文档都是以<htmI>开头,以</html>表示文档结尾,即根标签。

头部(head):描述浏览器所需的信息,如页面标题、关键词、说明等,开始标签,结束标签。

主体(body):包含网页所要展示的具体内容,以开始,以<body>开始,以</body>结束。

树形结构:整个文档通过标签嵌套形成一个树形结构。网络爬虫进行信息提取时,通常将HTML文档转换成树结构再进行选择。

• <html>:文件开始标签,表示该文件是以超文本标识语言(HTML)编写的。 <html>标签是成对出现的,首标签<html>和尾标签</html>分别位于文件的 最前面和最后面,文件中的所有文件和HTML标签都包含在其中。

• <head>:文件头部标签。习惯上,把HTML文件分为文件头和文件主体两个部 分。文件主体部分就是在Web浏览器窗口的用户区内看到的内容,而文件头部分 用来规定该文件的标题(出现在Web浏览器窗口的标题栏中) 和HTML文件的一 些属性,包含文件的标题、 编码方式及URL等信息。这些信息大部分是用于提供 索引、辨认或其他方面的应用。

• <body>:页面的主体标签,包含很多属性,如text设定页面文字颜色、bgcolor 设定页面背景颜色、background设定页面背景图像、bgproperties设定页面背景图 像为固定(不随页面的滚动而滚动)、link设定页面默认的链接颜色、alink设定鼠标正在单击时的链接颜色、vlink设定访问过后的链接颜色、topmargin设定页面的 上边距、leftmargin设定页面的左边距;等等。

• <title>:文件标题标签,表示该网页的名称,写在<head>与</head>中间的文本,作为窗口的名称显示在这个网页窗口的最上方。

• <meta>:元信息标签,提供关于HTML文档的元数据,一般用来定义页面信息 的名称、关键字、作者、字符编码、关键词、页面描述、最后修改时间等。meta 标签提供的信息是用户不可见的,不显示在页面中,不需要设置结束标签,在一 个尖括号内就是一个meta内容, 而在一个HTML头页面中可以有多个<meta>标签。 <meta>标签使用charset属性声明Web文档的字符编码。例如:<meta charset =utf-8>

<base>:用来指定页面中所有超链接的基准路径,
简化包含相对路径的超链接的转换过程。
例如,如果在p.html中有如下的<base>标签,
<base href="http://www.a.b.c/aaa/" />
那么,<img src="images/p2.gif">表示从
http://www.a.b.c/aaa/images/p2.gif
获得图片文件。

<link>:用于链接外部css样式表等其他相关外部资源。
包含属性:rel 必填,表明当前文档和外部资源的关系;
href 指明外部资源文件的路径,即告诉浏览器外部资源的位置;
type 说明外部资源的MIME 类型,如text/css;
title属性:ref=stylesheet时css样式会作为默认样式加载并渲染

<p>:定义段落。可以将要显示的文章内容放在<p>与</p>标签之间。
该标签会自动在段落前后添加一些空白,可以使用CSS来进行调整。
通常在Web页面中正文部分的各个段落都是通过该标签来表示。
例如:<p>This is a para.</p>•

<a> :定义超链接,用于从一张页面链接到另一张页面,
其最重要的属性是href,它指示链接的目标。
href是Hypertext Reference的缩写,意思是指定超链接目标的URL。

a标签的target属性:

① _self:默认值,在相同的框架或者当前窗口中打开链接

② _blank:在一个新的窗口中打开链接

③ _parent:在上一层窗口中打开链接

④ _top:会清除所有被包含的框架,并打开链接

<a href='http://www.baidu.com/'  target='_blank'>跳转到baidu</a> 
<img>:向网页中嵌入一幅图像,没有结束标签•两个必需属性:
• src 属性:规定显示图像的URL;
•绝对 URL:指向以Web站点根目录为参考基础的目录路径或者其他站点
•相对 URL:指向站点内的文件
• alt 属性:规定在图像无法显示时的替代文本,如
<img src="imgs/computer.jpg"  alt="笔记本电脑" />,
若地址错误则显示为:

• <ul>:无序列表标签,表示无序列表的整体,用于包裹li标签;ul标签中只允许包含li标签;
• <ol>:有序列表标签,表示有序列表的整体,用于包裹li标签;ol标签中只允许包含li标签;
• <li>:表示无序列表的每一项,用于包含每一行的内容;li标签可以包含任何内容;列表每一行前默认显示圆点

<div>:用来定义文档中的分区或节,把文档分割成为独立的部分,经常用于网页布局。div是division的简写,意为分割、区域、分组。

•该标签通常会使用id 或 class 属性设计额外的样式,

• id用于标识单独的唯一的元素,在页面里面只能出现一次,不能重复使用。定义id的css是用#号

• class用于元素组(理解为某一类元素),是一种全局属性,可用于任何HTML元素。其主要目的是为元素提供一个或多个类名,这些类名可以在CSS中引用,以添加样式,或者在JavaScript中引用,以操纵元素。可以在页面里面重复使用。定义class的css是用点。例如,在CSS中,可通过.classname选择器来应用样式:

 <div class="red-text">Hello,World!</div>
 .red-text {
       color:red;
 }

script>:用于在html页面内插入脚本。其type属性为必选的属性,用来指示脚本的 MIME 类型。下面的代码在html页面内插入javascript脚本,在网页中输出“HelloWorld!”。

<script type="text/javascript">document.write("Hello World!")</script>

CSS层叠样式表

层叠样式表单(Cascading Style Sheet):是一种标记语言,用于为HTML文档定 义布局。例如,CSS涉及字体、颜色、边距、高度、宽度、背景图像、高级定位等方面。运用CSS样式可以让页面变得美观。

从HTML 4开始使用,定义如何显示HTML元素。即使是相同的HTML文档,应用不同的CSS,从浏览器看到的页面外观也会不同。

属性选择器:通过属性来选择标签。这些属性既可以是标准属性(HTML中默认该有的属性, 例如input标签中的type属性),也可以是自定义属性。

在HTML中,通过各种各样的属性,可以给元素增加很多附加信息。例如,在一个HTML页面 中,插入了多个标签,并且为每个标签设定了如字体大小、颜色等。示例代码如下:

在HTML中为标签添加属性之后,就可以在CSS中使用属性选择器选择对应的标签,来改变样式。在使用属性选择器时,需要声明属性与属性值,声明方法如下:

其中att代表属性;val代表属性值。给标签定义属性和属性值时,可以任意定义属性。

如下代码就可以实现为相应的标签设置样式。

ID选择器:通过 HTML页面中的ID属性来选择增添样式,与类选择器的基本相同,但需要注意的是由于HTML页面 不能包含有两个相同的id标签,因此定义的ID选择器也就只能被使用一次。

 ID选择器前面有一个 “#”号。其语法如下:

类选择器:名称由用户自己定义,并以“.”号开头,定义的属性与属性值也要遵循css规范。要应用类别选择器的HTML标签,只需使用class属性来声明即可。其语法如下:

ID选择器引用id属性的值,而类选择器引用的是class属性的值。

在一个网页中标签的class属性可以定义多个,而ID属性只能定义一个。比如一个页面中只能有一个标签的ID的属性值为“intro”。

添加到HTML中的方式

•(1)内联样式:在相关的标签中使用样式属性,当特殊的样式需要应用到个别元素时可以使用;样式属性可以是任何CSS属性,主要使用的属性为style。例如:

<p style="color:blue">This is a paragraph.</p> 

设置段落颜色。

•(2)内部样式表:头部通过标签定义内部样式表

•(3)外部引用:当样式需要被很多页面引用时,可以使用独立的外部CSS文件,这样可以简单页面模式的设计。

<head>
    
<link rel="stylesheet" type="text/css" href="css/mystyle.css">
</head>

<link>标签中,“rel=stylesheet”,rel是relations的缩写,关联的意思,关联的是一个样式表(stylesheet)文档,它表示这个link在html文档初始化时将被使用。rel是指关联到一个stylesheet(样式表单)。这句话的意思就是在html文件里边引入了一个css的外部样式链接,type说的是类型是css,href是链接的地址,这个css文件叫做mystyle,在css这个文件夹里边。

Web页面的组织方式

• a1.html页面中超链接的3种写法:(当前目录为aaa) • (1)采用相对链接,访问a2.html

<p><img SRC="images/p1.gif"> <a href="a2.html"> a2</a></p>

• (2)采用相对链接,访问b1.html,..表示上级目录,此处即为虚拟根目录

<p><img SRC="images/p2.gif"><a href="..\bbb\b1.html"> b1</a></p>

• (3)采用http开始的完整URL绝对链接,访问b1.html

<p><img SRC="images/p3.gif"> 
 <a href="http://127.0.0.1:8080\bbb\b1.html"> b1</a> </p>

对于爬虫来说,在获取a1.html页面之后,要寻找其中的href超链接。对于绝对链接,只需要把href=后面的字符串提取出来即可。而对于相对超链接,没有完整的http,单纯从这个href所指定的链接是无法知道其真正的结果,需要进行超链接的转换。爬虫程序应该检查HTML文档中是否存在标签。 为了简化相对路径转换,用标签指定所有超链接基准路径。如在a1.html 中增加如下:

<base href=”http://127.0.0.1:8080/aaa/”/>
编码体系与规范(了解)

• 网页编码:编码就是按照规则对字符进行翻译成对应的二进制数,在计算器中运行 存储,用户看的时候(比如浏览器),在用对应的编码解析出来用户能看懂的;

• (1)ASCII:一个英文字母(不分大小写)占一个字节的空间。标准ASCII码使用 七位二进制编码(扩展的是用一个字节),表示美式英语中的可打印字符(例如数 字0-9、大小写英文字母、标点符号、运算符号、美元符号)以及控制字符(例如退 格、空格),编码范围为0~127。汉字等不能被表示。

• (2)中文字符编码。主要有gb2312、gbk以及gb18030。gb2312使用两个字节连 在一起表示一个汉字,两个字节中前一个称为高字节(范围0xA1-0xF7),后一个 为低字节(范围0xA1-0xFE)。gb2312共收录6763个汉字,每个汉字占两个字节。 gbk编码只识别中文,是gb2312的扩展,gbk兼容gb2312的所有内容同时又增加了 近20000个新的汉字(包括繁体字)和符号。

• (3)unicode:容纳世界上所有语言字符和符号的集合; 通常使用两个字节来编码, 称为UCS-2(Universal Character Set coded in 2 octets)。为了使unicode能表示更多的文字,人们提出了UCS-4使用四个字节编码。 unicode编码范围为0- 0x10FFFF,最大的字符需要至少三个字节来表示。为了解决编码字符集unicode在 网页中使用的效率问题,utf-8、utf-16等编码方式被提出。

• (4)utf-8(8-bit unicode Transformation Format)是一种针对unicode字符集的可变长度字符编码方式。utf-8对不同范围的字符使用不同长度的编码。其中,1个英 文字符 = 英文标点 = 1个字节,1个中文(含繁体) =中文标

• Python 3中的字符串默认的编码为unicode,因此,gbk、gb2312等字符编码与utf-8 编码之间都必须通过unicode编码才能互相转换。即在python中,使用encode()将 unicode编码为utf-8、gbk等,而使用decode()将utf-8、gbk等字符编码解码为 unicode

• >>> n='大数据' #unicode
• >>> g=n.encode('gbk') #gbk
• >>> u=n.encode('utf-8') #utf-8
• >>> g2=n.encode('gb2312') #gb2312
• >>> g2u=g.decode("gbk").encode("utf-8") #gbk转成utf-8

网络通讯

web服务器工作原理

• ( 1 ) 建 立 连 接 : 客 户 端 通 过 T C P / I P 协 议 建 立 到 服 务 器 的 T C P 连 接 。

• ( 2 ) 请 求 过 程 ( R e q u e s t ) : 客 户 端 向 服 务 器 发 送 H T T P 协 议 请 求 包 , 请 求 服 务 器 里 的 资 源 文 档 。 每 一 个 用 户 打 开 的 网 页 都 必 须 在 最 开 始 由 用 户 向 服 务 器 发 送 访 问 的 请 求 。 当 在 浏 览 器 输 入 U R L 后 , 浏 览 器 会 先 请 求 D N S 服 务 器 , 获 得 请 求 站 点 的 I P 地 址 ( 即 根 据 U R L 地 址 “ w w w . m i n g r i s o f t . c o m ” 获 取 其 对 应 的 I P 地 址 如 1 0 1 . 2 0 1 . 1 2 0 . 8 5 ) , 然 后 发 送 一 个 H T T P R e q u e s t ( 请 求 ) 给 拥 有 该 I P 的 主 机 。

• ( 3 ) 响 应 过 程 ( R e s p o n s e ) : 服 务 器 在 接 收 到 用 户 的 请 求 后 , 会 验 证 请 求的 有 效 性 , 然 后 向 用 户 发 送 相 应 的 内 容 。 即 为 网 页 服 务 器 接 收 用 户 访 问 请 求, 处 理 请 求 , 产 生 响 应 ( 即 把 处 理 结 果 以 H T M L 文 档 形 式 返 回 给 浏 览 器 ) , 客 户 端 接 收 到 服 务 器 的 相 应 内 容 后 , 浏 览 器 经 过 C S S 渲 染 , 以 一 种 较 好 的 效 果 呈 现 给 用 户 , 以 供 用 户 浏 览 。

• ( 4 ) 关 闭 连 接 : 客 户 端 与 服 务 器 断 开 。

robots协议(了解)

• 为了给Web网站提供灵活的控制方式来决定页面是否能够被爬虫采集,1994年搜索行业正式发布了一份行业规范,即Robots协议。

• Robots协议又称为爬虫协议、机器人协议等,其全称是Robots Exclusion Protocol, 即“网络爬虫排除协议”。是互联网爬虫的一项公认的道德规范。

• 访问许可策略:网站通过Robots协议告诉爬虫哪些页面可以抓取,哪些页面不能抓 取。该协议指定了某种标识的爬虫能够抓取的目录或不能抓取的目录。

• 具体约定:文件中包含一个或多个记录,每个记录由一行或多行空白行隔开。Useragent的使用方式是User-agent [agent_name],其中agent_name典型的有两种,即 *和具体的爬虫标识。Disallow和Allow的使用决定了不同的访问许可。一个目录如果没有显式声明为Disallow时,它是允许访问的。

• 在编写爬虫程序时,了解robots的拓展功能,对于设计更加友好的爬虫是非常有益的。这些拓展功能主要有:通配符的使用、抓取延时、访问时段、抓取频率和 Robots版本号。

robots.txt文件:访问许可写在robots.txt文件中,该文件放在网站的虚拟根目录中, 可以公开访问,即在浏览器打开网站后,在网站首页的地址后面添加“/robots.txt”。

• 超文本传输协议(Hyper Text Transfer Protocol):基于TCP/IP协议的应用层协议, 采用请求/响应模型,通过使用Web浏览器、网络爬虫或其他工具,客户端向服务器 上的指定端口(默认端口为80)发送一个HTTP请求,服务器根据接收到的请求向 客户端发送响应信息。

• HTTP是由万维网协会(World Wide Web Consortium)和Internet工作小组 IETF(Internet Engineering Task Force)共同制定的规范。

• HTTP/1.1是目前使用最广泛的HTTP协议版本,于1997年发布。HTTP/1.1与之前的 版本相比,改进主要集中在提高性能、安全性以及数据类型处理等方面。

• HTTP协议是用于从网络传输超文本数据到本地浏览器的传送协议,它能保证高效 而准确地传送超文本内容。

• HTTP是基于"客户端/服务器"架构进行通信的,HTTP的服务器端实现程序有httpd、 nginx等,客户端的实现程序主要是Web浏览器,例如Firefox、Internet Explorer、 Google Chrome、Safari、Opera等。此外,客户端的命令行工具还有elink、curl等。 Web服务是基于TCP的,因此为了能够随时响应客户端的请求,Web服务器需要监 听在80/TCP端口。这样客户端浏览器和Web服务器之间就可通过HTTP进行通信了。

• 请求方法:GET、POST、HEAD,规定客户端和服务器之间的通信类型。

• GET:最常见,一般用于获取或者查询资源信息;

• POST:多了以表单形式上传参数的功能(如登录),除了查询信息还可以修改信息。

HTTP报文

. request Message(请求报文):

客户端 → 服务器端

<method> <request-URL> <version> #请求方法、请求URL、协议版本
<headers> #头部、请求头、标头
 #回车换行,请求结束
<entity-body> #实体,请求体

请求体通过“param1=value1¶m2=value2”的键值对形式,将要传递的请求 参数(通常是一个页面表单中的组件值)编码成一个格式化串。

• 起始行、响应行:版本协议、状态码、原因短语;

• 响应头:包含服务器响应的各种信息,也是“属性名:属性值”形式;

• 响应体:是HTTP要传输的内容。根据响应信息的不同,响应体可以为多种类型的 数字数据,比如图片、视频、CSS、JS、HTML页面或者应用程序等。

一些常用的HTTP头部属性名:

• (1)Accept请求头表示可接受的响应内容。同时,与Accept首部类似的还有 Accept-Charset 、Accept-Encoding、Accept-Language等首部,分别表示客户端可接受的字符集、可接受的编码方式和可接受的语言。

• (2)User-Agent属性表示客户端的身份标识字符串。通过该字符串使得服务器能 够识别客户使用的操作系统及版本、CPU 类型、浏览器及版本、浏览器渲染引擎、 浏览器语言、浏览器插件等信息。

• (3)Content-Type:标明MIME类型。

• (4)Cookie:是请求报文中可用的属性,也是客户端最重要的请求头。Cookie存储了客户端的一些重要信息,例如身份标识、所在地区等,通常是一个文本文件。 在向服务器发送URL请求时,可以将文件内容读出,附加在HTTP的请求头中,可 以免去用户输入信息的麻烦。

• 超文本传输安全协议(Hypertext Transfer Protocol Secure):通过计算机网络进 行安全通信的传输协议,即是HTTP协议的安全版本,使用SSL/TLS加密。

URL

• uniform resource locator:统一资源定位符,是因特网的万维网服务程序上用于 指定信息位置的表示方法。

• 每一个URL指向一个独特的资源,可以是一个html页面,一个CSS文档,一个图 片、文件等 • URL的一般格式为(带方括号[]的为可选项):protocol://hostname[port]/path/[; parameters][?query]#fragment,即如"协议://授权/路径?查询" ,或者“协议://用户 名:密码@子域名.域名.顶级域名:端口号/目录/文件名.文件后缀?参数=值#标志” • 三个部分:前两部分用“://”隔开,2和3部分用“/”隔开;

• 绝对URL:URL显示文件的完整路径,这意味着绝对URL本身所在的位置与被引 用的实际文件的位置无关。 [2]

• 相对URL: 相对URL以包含URL本身的文件夹的位置为参考点,描述目标文件夹 的位置。如果目标文件与当前页面(也就是包含URL的页面)在同一个目录,那 么这个文件的相对URL仅仅是文件名和扩展名,如果目标文件在当前目录的子目 录中,那么它的相对URL是子目录名,后面是斜杠,然后是目标文件的文件名和 扩展名。 65 p URL 51

• HTTP URL的形式如下

http://<host>:<port>/<path>?<searchpart>

第三章

网络爬虫概述

爬虫概念

网络爬虫(Web Spider)又称之为网络机器人、网络蜘蛛,是一种通过既定规则(网络爬虫算法),能够自动(浏览 或者)抓取互联网信息的程序。

反爬机制

 为什么会有反爬机制?原因主要有两点:

• 第一,在大数据时代,数据是十分宝贵的财富,很多企业不愿意让自己的数据被别人免费获取,因此,很多企业 都为自己的网站运用了反爬机制,防止网页上的数据被爬走;

• 第二,简单低级的网络爬虫,数据采集速度快,伪装度低,如果没有反爬机制,它们可以很快地抓取大量数据, 甚至因为请求过多,造成网站服务器不能正常工作,影响了企业的业务开展。

爬虫工作基本原理

• 网络爬虫的基本工作流程如下:

• (1)获取初始的 URL,该 URL 地址是用户自己制订的初始爬取的网页。

• (2)爬取对应 URL 地址的网页时,获取新的 URL 地址。

• (3)将新的 URL 地址放入 URL 队列中。

• (4)从 URL 队列中读取新的 URL,然后依据新的 URL 爬取网页,同时从新的网页中获取新的 URL 地址,重复上 述的爬取过程。

• (5)设置停止条件,如果没有设置停止条件时,爬虫会一直爬取下去,直到无法获取新的 URL 地 址为止。设置了 停止条件后,爬虫将会在满足停止条件时停止爬取。

用Python实现http请求

Python实现HTTP请求有以下的3种常用的库

(1)urllib库

• urllib是Python标准库中用于网络请求的库,该库有四个模块,分别是

urllib.request,

urllib.error,

urllib.parse,

urllib.robotparser。

(2)urllib3库

• urllib3提供了很多python标准库里所没有的重要特性,如线程安全、连接池、客户端SSL/TLS验证、文件编码上传、HTTP重定向、压缩编码、HTTP/SOCKS代理等。

(3)requests库

第三方库requests自称"HTTP for Humans",使用更简洁更方便。requests继承了urlib2的所有特性,requests支持HTTP连接保持和连接池,支持使用cookie保持会话,支持文件上传,支持自动确定响应内容的编码,支持国际化的URL和POST数据自动编码。

urllib模块

• 解决:Python如何访问互联网

• urllib是URL和lib两个单词共同构成的,URL就是网页的地址,lib是library(库)缩写。

• urllib是Python自带模块,用于操作网页URL,并对网页的内容进行抓取处理。(测试连通性)

• 严格地讲,urllib并不是一个模块,它其实是一个包(package),包含四个模块,对服务器请求的发出、跳转、代理 和安全等内容:

• urllib.request:用于实现基本 HTTP 请求的模块,提供打开和读取URL,如身份验证、重定向和cookie等

• urllib.error:异常处理模块,如果在发送网络请求时出现了错误,可以捕获异常进行异常的有 效处理。包含 urllib.request抛出的异常,其中最基本的异常类是URLError • urllib.parse:提供URL解析和URL引用 • urllib.robotparser:解析robots.txt文件,判断网站是否可以爬取信息。

• urllib.parse:提供URL解析和URL引用。

• urllib.robotparser:解析robots.txt文件,判断网站是否可以爬取信息。

urllib模块发送请求:urlopen()

• urllib模块的request子模块,提供了一个urlopen()方法,通过该方法指定URL发送HTTP请求来获取数据。

• 访问网页的函数:urllib.request.urlopen( )

 参数说明:

• url:需要访问网站的URL完整地址。

• data:该参数默认为 None ,通过该参数确认请求方式。如果是None,表示请求方式为GET,否则请求方式为POST。 在发送 POST请求时,参数data需要以字典形式的数据作为参数值,并且需要将字典类型的参数值转换为字节类型 的数据才可以实现POST请求。(没有设置data参数时就是get请求)

• timeout:以秒为单位,设置超时。

①发送 GET 请求,读取文件

#导入库
import urllib.request 
#爬取网页并赋值给变量 
response = urllib.request.urlopen("http://www.jd.com") 
#读取网页全部内容 
#read()会把读取到的内容赋给一个字符串变量,无参数时表示读 取至文件结束为止 
html = response.read() 
print(html)

这跟在浏览器上使用“检查”功能看到的的内容是不一样的,因 为Python爬取的内容是以UTF-8编码的bytes对象,要还原为带中 文的HTML代码,需要对其进行解码,将它变成Unicode编码。 

②转码:utf-8到unicode
import urllib.request
response = urllib.request.urlopen("http://www.jd.com")
#以utf-8的编码对response.read()进行解码,以获取unicode
html = response.read().decode("utf-8") 
print(html)

③查看响应数据类型
import urllib.request
response = urllib.request.urlopen("http://www.jd.com")
print('响应数据类型为:',type(response))

④查看响应数据更多属性
import urllib.request
url ='http://www.jd.com'
response=urllib.request.urlopen(url=url)
print('响应数据类型为:',type(response))
print('响应状态码为:',response.status)
#Accept-Ranges表示服务器是否支持以byte为单位的一定资源范围的请求
print('响应头指定信息为:',response.getheader('Accept-Ranges'))
print('当前网页状态码为:',response.getcode())
print('当前网页的网址为:',response.geturl())
print('响应头所有信息为:',response.getheaders())  #返回一个包含服务器响应HTTP请求所发送的标头。

在使用 urlopen() 方法实现一个网络请求时,所返回的是一个“http.client.HTTPResponse” 对象。在 HTTPResponse 对象中包含可以获取信息的方法以及属性。

•例如请求一个文件的200byte—400byte的数据:

• Accept-Ranges:bytes 表示该资源支持byteurl='http://www.jd.com'形式资源范围请求

• Accept-Ranges:none则表示不支持

发送 POST 请求 (疑惑)
urllib.request.urlopen 
( url, data=None, [ timeout,]*, cafile=None, capath=None,cadefault=False, context=None)

• urlopen()方法在发送 POST请求时,参数data需要以字典形式的数据作为参数值,并且需要将字典类型的参数值转换为字节类型的数据。

•发送POST请求,需要设置data参数,该参数是bytes类型,所以需要使用bytes()方法,将原始字典形式数据的参数值,进行数据类型的转换。

•配合parse.urlencode。

•原始参数值为表单数据,是指通过表单让用户填写内容,然后提交到服务器上

• Urllib模块中提供了 parse子模块,主要用于解析URL,可以实现URL的拆分或者是组合。

• 支持多种协议的 URL 处理,如 file、ftp、gopher、 hdl、http、https

• urlencode()方法:接收一个字典类型的值

• 所以要想将URL进行编码需要先将请求参数定义为字典类型,然后再调用urlencode()方法进行请求参数的编码

• 编码后的请求地址为: http://httpbin.org/get?name=Jack&country=%E4%B8%AD%E5%9B%BD&age=30

• 地址中“%E4%B8%AD%E5%9B%BD&”内容为中文(中国)转码后的效果。 

import urllib.request    # 导入urllib.request模块 
import urllib.parse       # 导入urllib.parse模块 
url= 'https://www.httpbin.org/post' # POST请求测试地址 
# 将表单数据转换为bytes类型,并设置编码方式为UTF-8 
data = bytes(urllib.parse.urlencode({'hello' :'python'}),encoding='utf-8') 
response= urllib.request.urlopen(url=url,data=data) #发送网络请求   
print(response.read().decode('utf-8')) # 读取HTML代码并进行

Request类

• 有时在请求一个网页内容时,会发现无论通过GET、 POST以及其他请求方式,都会出现403或者404错误。

• 这种现象多数为服务器拒绝了您的访问,那是因为这 些网页为了防止恶意采集信息,所使用的反爬虫设置。

• 此时可以通过模拟浏览器的头部信息来进行访问,这样就能解决以上反爬设置的问题。

• 设置请求头是爬虫程序中必不可少的一项设置,大多 数网站都会根据请求头内容制订一些反爬策略。

• 如果要构建一个完整的网络请求,还需要在请求中添加Headers 、Cookies 以及代理 IP 等内容,这样才能更好的模拟一个浏览器所发送的网络请求。Request 类则可以构建一个多种功能的请求对象。

urllib.request.Request
(url,data=None, headers={},
 origin_req_host=None, 
unverifiable=False, 
method=None)

参数说明:

• url:需要访问网站的URL完整地址。

• data:该参数默认为None,通过该参数确认请求方式,

如果是None,表示请求方式为GET,否则请求方式为 POST。

在发送POST请求时,参数data需要以字典形式的数据作为参数值,并且需要将字典类型的参数值转换为字节类型的数据才可以实现POST请求。

• headers:设置请求头部信息,该参数为字典类型。添加请求头信息最常见的用法就是修改User-Agent来伪装成浏览器。

例如,

headers={'UserAgent':'Mozilla/5.0(WindowsNT10.0;WOW64)AppleWebKit/537.36(KHTML,likeGecko)Chrome/83.0.4103.61Sa fari/537.36'},表示伪装谷歌浏览器进行网络请求。

• method:用于设置请求方式,如GET、POST等,默认为GET请求(POST除了设置data,还需要再次明确method)

urllib.request.urlopen ( url, data=None, [ timeout,]*, cafile=None, capath=None, cadefault=False, context=None)
设置请求头

• 设置请求头参数是为了模拟浏览器向网页后台发送网络请求,这样可以避免服务器的反爬措施。

• 使用urlopen()方法发送网络请求时,其本身并没有设置 请求头参数,所以以https://www.httpbin.org/post请求测试地址发送请求时,返回的信息中headers将显示如图所示的默认值。

• User-Agent:中文名为用户代理,简称 UA,是一个特 殊字符串头,使得服务器能够识别客户使用的操作系统 及版本、CPU 类型、浏览器及版本、浏览器渲染引擎、 浏览器语言、浏览器插件等。

• 常常要用server抓资料时,都会碰到直接使用wget和curl 被服务器拒绝的状况。通常简单加个user-agent伪装一 下就会过了。

•所以在设置请求头信息前,需要在浏览器中找到一个有效的请求

头信息。

•【方法1】在浏览器地址栏输入

about:version

•显示:用户代理 Mozilla/5.0

(Windows NT 10.0; WOW64)

AppleWebKit/537.36 (KHTML,

like Gecko)

Chrome/94.0.4606.71

Safari/537.36 SE 2.X MetaSr 1.0

•【方法2】以谷歌浏览器为例,键盘中按下快捷键打开“开发者工具”,或者右键“检查”,然后选择Network选项,在请求列表Name中选择一项请求信息(如对应网),最后在Headers选项中找到请求头信息。

•如果需要设置请求头信息,首先通过Request类构造一个带有headers请求头信息的Request对象,然后为urlopen()方法传入Request对象,再进行网络请求的发送。

•【例】设置请求头的必要性

• 如果需要设置请求头信息,首先通过Request类构造一个带有headers请求头信息的Request对象,然后为urlopen() 方法传入Request对象,再进行网络请求的发送。

【例】Request类设置请求头发送POST请求

import urllib.request  # 导入urllib.request模块
import urllib.parse    # 导入urllib.parse模块
# 设定请求网址
url = 'https://www.httpbin.org/post'
# 将表单数据转换为bytes类型,并设置编码方式为utf-8
data = bytes(urllib.parse.urlencode({'hello': 'python'}), encoding='utf-8')
# 设定请求头信息
headers = {'User-Agent':'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/83.0.4103.61 Safari/537.36'}
# 创建Request对象
R = urllib.request.Request(url=url,data=data,headers=headers,method='POST')
# 发送网络请求
response = urllib.request.urlopen(R)
# 读取HTML代码并进行utf-8解码
print(response.read().decode('utf-8'))

urllib3模块

urllib3模块发送请求:request()

• 使用urllib3模块发送网络请求时,首先需要创建PoolManager对象,通过该对象调用request()方法来实现网络请求的发送。

request (method, url, fields = None, headers = None )

常用参数说明:

• method :必选参数,用于指定请求方式,如GET、POST、PUT等。使用urllib3模块向服务器发送POST请求时并不 复杂,与发送GET请求相似,只是需要在request()方法中将method参数设置为“POST” ,然后将fields参数设 置为字典类型的表单参数。

• url :必选参数,用于设置需要请求的URL地址。

• fields :可选参数,用于设置请求参数。

• headers :可选参数,用于设置请求头

GET请求

• 用urllib3发送请求,所返回的是一个“urllib3.response.HTTPResponse” 对象。

import urllib3    # 导入urllib3模块
url = "http://www.jd.com"
PM = urllib3.PoolManager()   # 创建连接池管理对象
r = PM.request('GET',url)    # 发送GET请求
print(r.status)                # 打印请求状态码
print('响应数据类型为:',type(r))  # 查看返回对象

#——————例1:可以合并,可设置参数——————
import urllib3    # 导入urllib3模块
url = "http://www.jd.com"
r = urllib3.PoolManager().request(method='GET',url=url)  # 创建连接池管理对象,发送get请求
# print(r.status)                # 打印请求状态码
# print('响应数据类型为:',type(r))  # 查看返回对象
print('响应对象的属性包括:',dir(r))
print('返回结果:',r.data.decode('utf-8'))

一个PoolManager对象就是一个连接池管理对象,通过该对象可以实现向多个服务器发送请求。

urlib3.disable_wamnings() 是一个Python库中的函数, 用于禁用SSL证书验证警告。 在使用urlib3库发送HTTPS 请求时,如果目标网站的 SSL证书不受信任,会出现 警告信息。使用该函数可以 禁用这些警告信息,但同时也会降低安全性。

#——————例2:使用PoolManager对象向多个服务器发送GET请求——————
import urllib3    # 导入urllib3模块
urllib3.disable_warnings()               # 关闭ssl警告
jingdong_url = 'https://www.jd.com/'     # 京东url地址
python_url = 'https://www.python.org/'   # Python url地址
baidu_url = 'https://www.baidu.com/'     # 百度url地址
PM = urllib3.PoolManager()             # 创建连接池管理对象
r1 = PM.request('GET',jingdong_url)    # 向京东地址发送GET请求
r2 = PM.request('GET',python_url)      # 向python地址发送GET请求
r3 = PM.request('GET',baidu_url)       # 向百度地址发送GET请求
print('京东请求状态码:',r1.status)
print('python请求状态码:',r2.status)
print('百度请求状态码:',r3.status)

POST请求

发送post请求同样使用request方法,只需要将request方法中的method参数设置为POST,将fields参数设置为 字典类型的表单参数。

#——————例3:使用request方法实现POST请求——————
import urllib3    # 导入urllib3模块
urllib3.disable_warnings()               # 关闭ssl警告
url = 'https://www.httpbin.org/post'    # post请求测试地址
params = {'name':'Jack','country':'中国','age':30}  # 定义字典类型的请求参数(随意写)
PM = urllib3.PoolManager()             # 创建连接池管理对象
r = PM.request('POST',url,fields=params)    # 发送POST请求
print('返回结果:',r.data.decode('utf-8'))   # 中国显示的是Unicode编码
print('返回结果:',r.data.decode('unicode_escape'))

使用request方法实现POST请求 • 发现:JSON信息中的form对应的数据为表单 参数,只是country所对应的并不是“中国” 而是一段Unicode编码,对于这样的情况,可 以将请求结果的编码方式设置为 “unicode_escape”。关键代码如下:

任意编码的字符串,如果内容是unicode码, 如:’\u53eb\u6211’ ,注意看乱码前面有个u, 这表示使用的unicode编码字符。使用 decode('unicode_escape')命令,对字符串内容 按照unicode解码后得到其对应的汉字。

重试请求

urllib3模块可以自动重试请求,这种相同的机制还可以处理重定向。在默认情况下request方法的请求重试次数为 3次,如果需要修改重试次数可以设置retries参数。

#——————例4:通过retries参数设置重试请求——————
import urllib3    # 导入urllib3模块
urllib3.disable_warnings()               # 关闭ssl警告
url = 'https://www.httpbin.org/get'    # get请求测试地址
PM = urllib3.PoolManager()             # 创建连接池管理对象
r = PM.request('GET',url)              # 发送GET请求,默认重试请求
r1 = PM.request('GET',url,retries=5)   # 发送GET请求,设置5次重试请求
r2 = PM.request('GET',url,retries=False) # 发送GET请求,关闭重试请求
print('默认重试请求次数:',r.retries.total)
print('设置重试请求次数:',r1.retries.total)
print('关闭重试请求次数:',r2.retries.total)

处理响应信息

发送网络请求后,将返回一个 HTTPResponse对象,通过该对象中的info()方法即可获取HTTP 响应头信息,该信息为字典(diet) 类型的数据,所以需要通过for循 环进行遍历才可清晰的看到每条 响应头信息内容。

• https://www.httpbin.org/get

• 查看网页的响应头,发现共有7项

#——————例5:通过info()方法获取响应头信息——————
import urllib3    # 导入urllib3模块
urllib3.disable_warnings()               # 关闭ssl警告
url = 'https://www.httpbin.org/get'    # get请求测试地址
PM = urllib3.PoolManager()             # 创建连接池管理对象
r = PM.request('GET',url)              # 发送GET请求,默认重试请求
response_header = r.info()               # 获取响应头
print(response_header.keys())
for key in response_header.keys():      # 循环遍历打印响应头信息
    print(key,':',response_header.get(key))

for key in response_header.keys():      # 循环遍历打印响应头信息
    print(key,':',response_header.get(key))

设置请求头

请求头信息获取完成以后,将“User-Agent”设置为字典(dict)数据中的键,后面的数据设置为字典(dict)中value。

#——————例6:设置请求头信息——————
import urllib3    # 导入urllib3模块
urllib3.disable_warnings()               # 关闭ssl警告
url = 'https://www.httpbin.org/get'    # get请求测试地址
# 定义火狐浏览器请求头信息
headers = {'User-Agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:77.0) Gecko/20100101 Firefox/77.0'}
PM = urllib3.PoolManager()                   # 创建连接池管理对象
r = PM.request('GET',url,headers=headers)    # 发送GET请求
print(r.data.decode('utf-8'))                  # 打印返回内容

requests模块

由于requests模块为第三方模块,所以在使用requests模块时需要通过执行命令“pip install requests” 进行该 模块的安装。如果使用了 Anaconda则不需要单独安装requests模块。

使用requests模块实现GET请求时可以使用两种方式来实现,一种是带参数,另一种为不带参数。

requests.get (url, params=None, **kwargs)

参数说明:

• url:需要访问网站的URL完整地址

• params:该参数默认为 None ,是请求 url 时的额外参数,可以是字典或者字节流格式

• **kwargs:用于控制请求的一些附属特性,包括headers、cookies、params、proxies等,总共有12个控制参数。

(1) headers: Python 中的字典型变量,可以模拟任何浏览器标识来发起url。

(2) cookies :字典或CookieJar ,指的是从HTTP中解析 Cookie

(3) timeout :用于设定超时时间,单位为秒。当发起 GET请求时可以设置timeout 时间,如果在timeout时间内 请求内容没有返回,将产生一个timeout异常

(4) proxies :字典,用来设置访问代理服务器

(5) params :字典或字节序列,作为参数添加到url中,可以把一些键值对以?key1=value1& key2=value2式添加到url 

【例1】以京东为例,实现不带参数的GET网络请求
#——————例1:不带参数的get请求——————
import requests    # 导入网络请求模块request
response = requests.get('http://www.jd.com')  # 发送网络请求
response.encoding = 'utf-8' # 对响应结果进行UTF-8编码
# print(response.text)  # 以文本形式打印网页源码
print('网页源码为:',response.content)          # 以字节流形式打印
print(dir(response))
# html = response.read()  #报错,没有read方法

注意:需要设定为页面的编码,即页面源代码中的charset的值。只有当设定编码和页面本身的编码方式一致时,通过 Response对象的text属性才能获得没有乱码的HTML文本信息。在没有对响应内容进行UTF-8编码时,网页源码中的中文信息可能会出现如图所示的乱码。

import requests    # 导入网络请求模块request
response = requests.get('http://www.jd.com')  # 发送网络请求
print('响应数据类型为:', type(response))       # 获取响应类型
print('响应状态码为:', response.status_code)  # 打印状态码
print('请求的网络地址为:', response.url)          # 打印请求url
print('头部信息为:', response.headers)      # 打印头部信息
print('cookie信息为:', response.cookies)      # 打印cookie信息
import requests
url='http://www.jd.com'  #设置url变量方式也可以
response = requests.get(url)
print('响应状态码为:', response.status_code)
【例2】下载百度首页中的Logo图片

• 使用requests模块中的get()函数不仅可以获取网页中的源码信息,还可以获取二进制文件。但是获取二进制文件时,需要使用Response.content属性获取bytes类型的数据,然后将数据保存在本地文件中。

#——————例2:下载百度首页中的Logo图片——————
import requests    # 导入网络请求模块requests
response = requests.get('https://www.baidu.com/img/bd_logo1.png?where=super')
print(response.content)                # 打印二进制数据
with open('百度logo.png','wb')as f:   # 通过open函数将二进制数据写入本地文件
    f.write(response.content) 

实现请求地址带参:如果需要为GET请求指定参数时,可以直接将参数添加在请求地址URL的后面,然后用问号 (?) 进行分隔,如果一个URL地址中有多个参数,参数之间用“&”进行连接

URL参数:查询字符串

• 查询字符串(URL参数)是指在URL的末尾加上用于向服务器发送信息的字符串(变量)。

• 将英文的'?'放在URL的末尾,然后再加上键值对'参数=值',可以使用'&'符号进行分隔加多个参数。

• 在网页开发和设计过程中,URL字符串参数的应用非常广泛,它们可以提供很多有用的信息,例如搜索关键字, 用户身份验证信息等。可以帮助网页开发者和设计者更好地控制和管理网页的呈现。通过合理使用URL字符串参 数,可以让用户更方便地找到想要的内容,提升用户体验和网页的可用性。 

配置params参数:requests模块提供了传递参数的方法,允许使用params关键字参数以一个字符串字典来提供这些参数。

#——————例3:实现GET请求地址带参——————
import requests    # 导入网络请求模块requests
response = requests.get('http://httpbin.org/get?name=Jack&age=30')
print(response.text)

#——————例4:实现GET请求地址带参——————
import requests    # 导入网络请求模块requests
data = {'name':'Jack', 'age': '25'}
response = requests.get('http://httpbin.org/get', params = data)
print(response.text)
【例4】实现GET请求地址带参
import requests    # 导入网络请求模块requests
url = 'http://httpbin.org/get'
data = {'name':'Jack', 'age': '25'}
response = requests.get(url=url, params = data)
print(response.text)

import requests
base_url = 'http://httpbin.org'
param_data = {'user':'xmu','password':'123456'}
response = requests.get(base_url+'/get',params=param_data)
print(response.url)
print(response.status_code)

【例5】实现POST请求

POST请求:POST请求方式也叫作提交表单,表单中的数据内容就是对应的请求参数。

【例6】添加请求头模拟浏览器头部信息访问网页

复杂的网络请求:requests模块将这一系列复杂的请求方式进行了简化,只要在发送请求时设置 应的参数即可实 现复杂的网络请求。

【例7】爬取百度新闻

① 获取网页源代码

可以看到其并没有获取到真正的网页 源代码,这是因为这里的百度资讯网 站只认可浏览器发送过去的访问,而 不认可直接通过Python发送过去的访 问请求——需要设置下requests.get()中的 headers参数,用来模拟浏览器进行访 问。

②设置headers

③反爬:2022.8以来,百度新闻通过requests库不好爬了,此时可以把网址url中的https改成http(ssl证书认证问 题),或者使用selenium库,或者加上ip代理反爬

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值