web抓取,利用程序下载处理web,让在python中抓取网页变得容易
webbrowser :python自带的浏览器
requests:从因特网上下载文件和网页
Beautiful Soup:解析HTML,即网页编写的格式
selenium:启动并控制一个web浏览器,selenium能填写表单,并模拟鼠标在这个浏览器里点击
利用webbrowser 模块:
import webbrowser webbrowser.open('http://www.cnblogs.com/zsc329/')
利用requests模块从web上下载文件:
requests不是自带的,先安装
requests.get()函数
import requests res=requests.get('http://www.cnblogs.com/zsc329/') print(type(res)) print(res.status_code==requests.codes.ok) #通过res.status_code返回一个数字属性代表请求状态 #requests.codes.ok请求成功,OK的编码是200,没找到的编码是404 print(len(res.text)) #下载的页面作为一个字符串保存在text变量中 print(res.text[:200]) #取读前面200位
结果:
<class 'requests.models.Response'> True 5624 <!DOCTYPE html> <html lang="zh-cn"> <head> <meta charset="utf-8"/> <meta name="viewport" content="width=device-width, initial-scale=1" /> <title>朝游碧海暮苍梧 - 博客园</title> <link type="text/css" rel
检查错误
如res.status_code属性可以检查它是否等于requests.codes.ok了解下载是否成功,有一种更简单的方法
res.raise_for_status()
如果下载文件出错会抛出异常,否则则什么也不做
可以用try语句将其包起来
try: res.raise_for_status() except Exception as err: print("wrong:"+str(err))
结果:
wrong:404 Client Error: Not Found for url: http://www.cnblogs.com/zsc/
保存下载文件
先试用之前的直接写入字符串res.text
import requests res=requests.get('http://www.cnblogs.com/zsc329/') res.raise_for_status() resfile=open('Resfilenote.txt','w') resfile.write(res.text) resfile.close()
发现编码问题,出现大量乱码,采用写入bytes数据类型
import requests res=requests.get('http://www.cnblogs.com/zsc329/') res.raise_for_status() resfile=open('Resfilenote2.txt','wb') for i in res.iter_content(): resfile.write(i) resfile.close()
完整过程:
先调用requests.get()
用wb调用open,以二进制的方式写入一个新文件
利用对象的iter_content()方法做循环
每次迭代调用write()
close()
注:iter_content()是在循环中返回一段内容,每一段都是bytes数据类型,你需要指定一段包含多少内容
HTML
html文件是纯文本文件,带有.html文件扩展名,这种文件中的文本被标签(<>尖括号包围的单词)环绕,标签代表格式
一个开始标签和一个结束标签包围的文本称之为元素
使用开发者工具F12了解网页的源码
用Beautiful Soup模块解析HTML:
一个灵活又方便的网页解析库,处理高效,支持多种解析器。
利用它就不用编写正则表达式也能方便的实现网页信息的抓取
import requests,bs4 res=requests.get('http://www.cnblogs.com/zsc329/') res.raise_for_status() btemp=bs4.BeautifulSoup(res.text,"html.parser") print(type(btemp))
如果不加"html.parser",会出现警告,没有明确规定,所以我使用最好的HTML解析器这个系统(“HTML解析器”)。
这通常不是问题,但是如果你在另一个系统上运行这个代码,或者在不同的虚拟环境中运行,它可能会使用不同的解析器,并且表现得不同。
UserWarning: No parser was explicitly specified, so I'm using the best available HTML parser for this system ("html.parser"). This usually isn't a problem, but if you run this code on another system, or in a different virtual environment, it may use a different parser and behave differently. <class 'bs4.BeautifulSoup'> The code that caused this warning is on line 4 of the file D:/pyfile/pythonlearn/webmessage/requestmode.py. To get rid of this warning, change code that looks like this: BeautifulSoup(YOUR_MARKUP}) to this: BeautifulSoup(YOUR_MARKUP, "html.parser") markup_type=markup_type))
用select()方法寻找元素
针对你要寻找的元素调用method()方法,传入一个字符串作为css选择器,css就像正则表达式,指定了模式,实在HTML页面中寻找,而不是普通的文本字符串
选择器的例子:
soup.select('div') 匹配所有名为div的元素
soup.select('#author') 匹配id属性为author的元素
soup.select('.notice') 所有使用CSS class属性名为notice的元素
import requests,bs4 res=requests.get('http://www.cnblogs.com/zsc329/') res.raise_for_status() btemp=bs4.BeautifulSoup(res.text,"html.parser") elems=btemp.select('#home') #通过对象处理 print(len(elems)) #只有一个可选对象 print(elems[0].get_text()) #返回元素的文本或者内部的HTML,一个元素的文本是在开始与结束中间的内容 #输出规整文本 print('-'*80) print(str(elems[0])) #返回一个字符串,包含开始与结束的标签 #输出类似源代码 print(elems[0].attrs) #返回一个字典,包含该元素的属性‘id’ #此处是{'id': 'home'}
#获取数据 print(elems[0].get('id')) #home
用selenium控制浏览器
直接控制浏览器,实际点击链接,实际点击链接,填写登录信息
print(elems[0].get('id'))
#home