爬虫学习

爬虫学习

1、 第一只爬虫:

import requests
r = requests.get(
"http://www.baidu.com")

# HTTP请求的返回状态,200表示连接成功,404表示失败
print(r.status_code)

# # r的类型,属于Response
# print(type(r))
#
# #
请求的头部部分
# print(r.headers)


# HTTP
响应内容的字符串形式,即,url对应的页面内容
#
基本会出现乱码
print(r.text)

# HTTP header中猜测的响应内容的编码方式
print(r.encoding)

# 从内容中分析出的响应内容编码方式(备选编码方式)
print(r.apparent_encoding)

# 解决乱码问题
r.encoding = "utf-8"
print(r.text)

# HTTP响应内容的二进制形式
print(r.content)

 

 

爬虫基本框架:

import requests


def getHTMLText(url):
   
try:
       
r = requests.get(url, timeout=30)
       
r.raise_for_status()  # 如果状态不是200,引发HTTPEroor异常
       
r.encoding = r.apparent_encoding
       
return r.text
   
except:
       
return "产生异常"


if __name__ == "__main__"# TODO 有点不懂
   
url = "http://www.baidu.com"
   
print(getHTMLText(url))

 

 

 

 

 

robots协议:

查看方式:http://*****.com/robots.txt

 

 

爬取京东华为手机信息:

1、简洁版

import requests
r = requests.get(
"https://item.jd.com/4203985.html")

# 检查访问是否正常
print(r.status_code)

# 由头部检查网页编码方式
print(r.encoding)
# 提取text里边从01000的字符信息
print(r.text[:1000])

 

2、     安全版

import requests
url =
"https://item.jd.com/4203985.html"
try:

   
r = requests.get(url)
    r.raise_for_status()
    r.encoding = r.apparent_encoding
    print(r.text[:1000])
except:
   
print("爬取失败!")

 

 

 

爬取亚马逊:(模拟浏览器,向网站发起请求)

说明:针对不对爬虫开放的网站进行爬取

 

1、  简洁版:

import requests

"""解决办法,修改User-Agent为一个浏览器字段
Mozilla/5.0
是一个标准浏览器字段(被多种浏览器采用)
"""
kv = {"user-agent": "Mozilla/5.0"}
url =
"https://www.amazon.cn/dp/B01M8L5Z3Y/ref=sr_1_1?s=books&ie=UTF8"\
     
"&qid=1519982182&sr=1-1&keywords=%E6%9E%81%E7%AE%80"

# headers 方法修改。。。请求信息
r = requests.get(url, headers=kv)
print(r.encoding)                         # url头部为utf-8格式
print(r.status_code)
# 'user-agent': 'Mozilla/5.0'  表明修改成功
print(r.request.headers)
print(r.text[:1000])

 

 

2、  安全版

 

import requests
url =
"https://www.amazon.cn/dp/B01M8L5Z3Y/ref=sr_1_1?s=books&ie=UTF8"\
     
"&qid=1519982182&sr=1-1&keywords=%E6%9E%81%E7%AE%80"
try:
   
kv = {"user-agent": "Mozilla/5.0"}
   
r = requests.get(url, headers=kv)
   
r.raise_for_status()
    r.encoding = r.apparent_encoding
    print(r.text[:1000])
except:
   
print("爬取失败!")

 

 

百度360搜索关键字提交:

说明:使用360搜索时,把wd修改为q就行了,其他都一样

 

1、  简洁版

 

import requests
kv = {
"wd": "python"}
r = requests.get(
"http://baidu.com/s", params=kv)
# 访问状态
print(r.status_code)

# 发给百度的url实际上是什么
print(r.request.url)

 

2、  安全版

 

import requests
keyword =
"python"
try:
   
kv = {"wd":keyword}
   
r = requests.get("http://baidu.com/s", params=kv)
   
print(r.request.url)
   
r.raise_for_status()
    # 显示爬取的文本长度
   
print(len(r.text))
except:
   
print("爬取失败!")

 

爬取国家地理图片:

1、  简洁版

 

import requests
path =
"D:/abc.jpg"
url = "http://img0.dili360.com/rw9/ga/M00/02/AB/wKgBzFQ26i2AWujSAA_-xvEYLbU441.jpg"
r = requests.get(url)
print(r.status_code)
# print(r.text)

#
打开一个文件,并把它定义为一个文件标志符f
with open(path, "wb") as f:
   
# r.content表示返回内容的二进制形式,再使用write把他写出了
   
f.write(r.content)
 
  f.close()

 

2、  安全版

 

import requests
import os  # TODO 不会
url = "http://img0.dili360.com/rw9/ga/M00/48/4E/wKgBzFllve2AO9VBAEzNdvr41Hs146.tub.jpg"
# 定义一个根目录
root = "D://pics//"
# 定义本地路径的文件名称,而且与网络文件名最后一部分相同
path = root +url.split("/")[-1# TODO 不会
try:
   
# 如果根目录不存在,就建立一个这样的目录
   
if not os.path.exists(root):
       
os.mkdir(root)
    # 判断文件存不存在,如果文件不存在就从网上获取这样一个文件
   
if not os.path.exists(path):
       
r = requests.get(url)
        with open(path, "wb") as f:
           
f.write(r.content)
            f.close()
            print("文件保存成功!")
   
else:
       
print("文件已经存在!")
except:
   
print("爬取失败!")

 

 

IP地址归属地自动查询:

1、  简洁版

 

import requests
kv = {
"user-agent": "Mozilla/5.0"}
url =
"http://m.ip138.com/ip.asp?ip="
r = requests.get(url + "202.204.80.112")
r = requests.get(url
, headers=kv)
print(r.status_code)
print(r.request.headers)
r.encoding = r.apparent_encoding
print(r.text[-500:])

 

2、  安全版

 

import requests
url =
"http://m.ip138.com/ip.asp?ip="
try:
   
r = requests.get(url + "202.204.80.112")
   
r.raise_for_status()
    r.encoding = r.apparent_encoding
    print(r.text[-500:])
except:
   
print("爬取失败!")

 

 

beautifulsoup库安装:

import requests
r = requests.get(
"https://python123.io/ws/demo.html")
print(r.text)
demo = r.text

# 导入beautiful
from bs4 import BeautifulSoup
# demo进行解析(使用html.parse解释器进行解析)
soup = BeautifulSoup(demo, "html.parser")
print(soup.prettify())

 

 

信息提取:

说明:提取网站源码中的网址链接

# 提取HTML中所有的url链接
import requests
from bs4 import BeautifulSoup

r = requests.get(
"https://python123.io/ws/demo.html")
demo = r.text
soup = BeautifulSoup(demo
, "html.parser")
for link in soup.find_all("a"):
   
print(link.get("href"))

 

 

基于bs4库的HTML内容查找方法:                        

 

import requests
from bs4 import BeautifulSoup

r = requests.get(
"https://python123.io/ws/demo.html")
demo = r.text
soup = BeautifulSoup(demo
, "html.parser")

"""BeautifulSoup库提供了一个方法,如下(查找信息)
<>.find_all(name, attrs, recursive, string, **kwargs)
返回一个列表类型,储存查找的结果

name
:对标签名称的检索字符串
attrs:
对标签属性值的检索字符串,可标注属性检索
recursive:
是否对某一个标签子孙所有节点进行搜索,默认是True(是一个布尔类型的值)
string
:对<>..</>中的字符串区域的检索字符串

"""

"""   
name方法     """
# # 查找a 标签内容
# print(soup.find_all("a"))
# #
查找a b 两个标签内容
# print(soup.find_all(["a", "b"]))
#
# #
查看有多少个标签(tag
# for tag in soup.find_all(True):
#     
print(tag.name)
#
# print("")
# """若只显示以b开头的标签(tag,
#
这里需要正则表达式库
# """
# #
导入正则表达式库
# import re
# for tag in soup.find_all(re.compile("b")):
#    
print(tag.name)

"""    attrs 方法     """
# # 输出一个带有course属性值的标签
# print(soup.find_all("p", "course"))
# print("")
#
# #
查找某个属性值=**,作为查找依据(查找必须十分精确,不然返回空列表)
# print(soup.find_all(id="link1"))
# print("")
#
# """
针对根据属性查找必须十分精确,解决措施(导入正则表达式)
#
进行比较模糊的查找
# """
# import re
# print(soup.find_all(id=re.compile("link"))) 
# 查找内容明显比上面多

"""    recursive方法   """
# print(soup.find_all("a"))
# #
检查a 标签下的子节点没有内容,返回空列表[]
# print(soup.find_all("a", recursive=False))

"""   string   """
# print(soup)  # 查看一下soup完整信息
# print("")
# #
同样查找依据必须十分精确(输入的字符串必须精确)
# print(soup.find_all(string="Basic Python"))
# print("")
# #
同样如果引入正则表达式,就可以进行模糊检索soup里的内容
# import re
# print(soup.find_all(string=re.compile("python")))

中国大学排名定向爬虫:

程序结构设计:

步骤一: 从网络上获取大学排名网页内容
步骤二:提取网页内容中的有用信息并把他放到合适的数据结构中
步骤三:利用数据结构展示并输出结果

 

import requests
from bs4 import BeautifulSoup
import bs4

"""获取url信息,输出url内容"""
def getHTMLText(url):
   
try:
       
r = requests.get(url, timeout=30)
       
r.raise_for_status()
        r.encoding = r.apparent_encoding
        return r.text
   
except:
       
return ""

"""
将这一个页面放到ulist"""
def fillUnivList(ulist, html):
   
# 解析HTML
   
soup =BeautifulSoup(html, "html.parser")
   
# 解析htmltbody所在位置,在tbody标签中找到每一所大学对应的tr标签
   
for tr in soup.find("tbody").children:

       
# tr标签中找到其中td标签的信息,并把需要的标签加到列表中
       
# isinstancebs4库中方法,筛选tr中有标签的信息(排除没有标签的信息)
       
if isinstance(tr, bs4.element.Tag):
           
tds = tr("td")
           
ulist.append([tds[0].string, tds[1].string, tds[2].string])

"""ulist信息打印出来"""
def printUnivList(ulist, num):
   
# 打印表头
   
print("{:^10}\t{:^6}\t{:^10}".format("排名", "学校名称", "总分"))
   
for i in range(num):
       
u = ulist[i]
        print("{:^10}\t{:^6}\t{:^10}".format(u[0], u[1], u[2]))


# 主函数
def main():
   
uinfo = []
    url = "http://zuihaodaxue.cn/shengyuanzhiliangpaiming2018.html"
   
html =getHTMLText(url)
   
fillUnivList(uinfo, html)
   
printUnivList(uinfo, 20# 获取20所学校排名


main()

 

Beautiful Soup库:

bs类基本元素:

Tag:标签,基本信息组织单元,分别用<>和</> 标明开头和结尾

Name:标签的名字,<>…</p>的名字是’p’ ,格式:<tag>.name

Attributes:标签属性,字典形式组织,格式<tag>.attrs

NavigableString: 标签内非属性字符串,<>…</>中字符串,格式:<tag>.string

Comment:标签内部字符串的注释部分,一种特殊的Comment类型

 

from bs4 import BeautifulSoup
import requests
r = requests.get(
"https://python123.io/ws/demo.html")
print(r.text)
print("")
demo = r.text
soup = BeautifulSoup(demo
, "html.parser")
print(soup.title)  # 打印title标签
print("")

# # a 标签
# tag = soup.a
# print(tag)

# #
获取a 标签名字、a父亲的名字(p)、a爷爷标签的名字(body)
# print(soup.a.name)
# print(soup.a.parent.name)
# print(soup.a.parent.parent.name)

#
标签中非属性字符串,NavigableString: 标签内非属性字符串,<>…</>中字符串,格式:<tag>.string

# comment
注释
newsoup = BeautifulSoup()

 

 

基于bs4库的HTML内容遍历方法:

from bs4 import BeautifulSoup
import requests
r = requests.get(
"https://python123.io/ws/demo.html")
# print(r.text)
print("")
demo = r.text
soup = BeautifulSoup(demo
, "html.parser")


"""标签树的下行遍历:.contents指将标签所有子节点存入列表
   
.children指用于循环遍历儿子节点
   
.descendants 子孙节点的迭代类型,包含所有子孙节点,用于遍历
"""
# # .contents用法
#
# # head
标签、以及他的儿子节点
# print(soup.head)
# print("")
# print(soup.head.contents) 
# 儿子节点
# #
查看body 标签儿子的信息
# print(soup.body.contents)
# print(len(soup.body.contents)) 
# 获取body 标签儿子的数量(5个)
# print(soup.body.contents[1]) 
# 获取body 标签儿子节点的第二个

# # .children
用法
# for child in soup.body.children:
#    
print(child)

# # .descendants用法
# for child in soup.body.descendants:
#    
print(child)

"""标签树的上行遍历
.parent
节点的父亲标签
.parents
节点的先辈(包含父亲及其以上)标签的迭代类型,用于循环遍历先辈节点
"""

# # parent用法
# print(soup.title.parent) 
# title的父亲是head标签
# print("")
# print(soup.html.parent) 
#html 标签是最高级的标签类型,他的父亲就是自己
# print("")
# print(soup.parent) 
# soup本身就是一种特殊标签,他的父亲是空的

# #
标签树的上行遍历
# for parent in soup.a.parents:
#    
print(parent)
# else:
#     print(parent.name)

"""标签树的平行遍历(只能发生在同一个父亲节点下的各节点间)
.next_sibling:
返回按照HTML文本顺序的下一个平行节点标签
.previous_sibling:
返回。。。上一个。。
.next_siblings:
迭代类型,返回按照HTML文本顺序的后续所有平行节点标签
.previous_siblings:
迭代类型,。。。前续。。。
"""
# print(soup.a.next_sibling)  # 标签可以是字符串
# print(soup.a.next_sibling.next_sibling) 
# a的下下个标签
# print(soup.a.previous_sibling) 
# a的上一个标签
# print(soup.a.previous_sibling.previous_sibling) 
# a的上上一个标签
# #
标签树的遍历
# for sibling in soup.a.next_siblings: 
#遍历后续节点
#    
print(sibling)
# for sibling in soup.a.previous_siblings: # 遍历前续节点
#    
print(sibling)

 

 

 

 

基于bs4库的HTML格式化:

from bs4 import BeautifulSoup
import requests
r = requests.get(
"https://python123.io/ws/demo.html")
# print(r.text)
print("")
demo = r.text
soup = BeautifulSoup(demo
, "html.parser")

# soup.prettify() 用于给标签增加换行符,使输出内容更清晰(即格式化)
print(soup.prettify())
print("")
print(soup.a.prettify())

 

HTML:

HTML是www(World Wide Web)的信息组织方式

 

正则表达式:(regular expression    .re)

变化最大的是年龄说明:正则表达式是用来简洁表达一组字符串的表达式

不把劳动作为第一生产力优势:简洁,可以简单地表达很大一个字符串的特征

 

 

re库基本使用:

"""
re
库的函数用法:一次性使用
解释:pattern:正则表达式的字符串或原生字符串表示
    
string:待匹配字符串
    
flags:正则表达式使用时的控制标记
    
maxsplit:最大分割数,剩余部分作为最后一个元素输出
    
repl:替换匹配字符串的字符串
    
count:匹配的最大次数

re.search()  
在一个字符串中搜索匹配正则表达式的第一个位置,返回match对象
格式:re.search(pattern,string, flags=0)
re.match()  
在一个字符串的开始位置起匹配正则表达式,返回match对象
格式:re.match(pattern,string, flags=0)
re.findall()  
搜索字符串,以列表类型返回全部能匹配的子串
格式:re.findall(pattern,string, flags=0)
re.split() 
 将一个字符串按照正则表达式匹配结果进行分割,返回列表类型
格式:re.findall(pattern,string, maxsplit=0, flags=0)
re.finditer()  
搜索字符串,返回匹配结果的迭代类型,每个迭代元素是match对象
re.finditer(pattern, string, flags=0)
re.sub()  
在一个字符串中替换所有匹配正则表达式的子串,返回替换后的字符串
re.finditer(pattern, repl, string, count=0, flags=0)
"""

# # search函数
# import re
# match = re.search(r"[1-9]\d{5}", "BLT 100081")
# if match:
#    
print(match.group(0))

# # match函数
# import re
# match = re.match(r"[1-9]\d{5}", "BLT 100081")
# if match:
#    
# 匹配结果是空,无法输出结果
#    
print(match.group(0))
# print("")
# match = re.match(r"[1-9]\d{5}", "100081 BLT")
# if match:
#     # 正常输出
#    
print(match.group(0))

# # findall函数
# import re
# ls = re.findall(r"[1-9]\d{5}", "BLT100081 TSU100084")
# #
返回一个列表
# print(ls)

# # split
函数
# import re
# #
输出不匹配的字符串部分
# print(re.split(r"[1-9]\d{5}", "BLT100081 TSU100084"))
# #
只匹配第一个
# print(re.split(r"[1-9]\d{5}", "BLT100081 TSU100084",maxsplit=1))

# # finditer
函数
# import re
# for m in re.finditer(r"[1-9]\d{5}", "BLT100081TSU100084"):
#    
if m:
#         print(m.group(0))

# sub函数
import re
print(re.sub(r"[1-9]\d{5}", ":zipcode", "BLT100081 TSU100084"))





"""
re
库的面向对象用法(先编译):多次使用,方法   regex = re.compile(pattern, flags=0)
regex(正则表达式)
pattern
表示正则表达式的字符串或原生字符串,flags表示正则表达式使用时的控制标记
re
库的等价用法:(方法同上)
regex.search():
regex.match():
regex.findall():
regex.split():
regex.finditer():
regex.sub():
"""

 

 

淘宝商品价格爬取:

import re
import requests


# 获得页面
def getHTMLText(url):
   
try:
       
r = requests.get(url, timeout=30)
       
r.raise_for_status()  # 如果状态不是200,引发HTTPEroor异常
       
r.encoding =r.apparent_encoding
       
return r.text
   
except:
       
return ""


# 解析页面,获取商品名称、价格
def parsePage(ilt, html):
   
try:
       
plt = re.findall(r'\"view_price\"\:\"[\d\.]*\"', html)  # TODO 为什么把高亮的斜杠 \ 去掉,程序还可以运行
       
tlt = re.findall(r'\"raw_title\"\:\".*?\"', html)
       
for i in range(len(plt)):
           
# eval函数可以将获取的字符串的双引号或单引号去掉
           
# spilt函数使用:分割字符串,获得键值对的后半部分
           
price = eval(plt[i].split(':')[1])
           
title = eval(tlt[i].split(':')[1])
           
ilt.append([price, title])
   
except:
       
print("")


# 将商品信息输出在屏幕上
def printGoodList(ilt):
   
# tplt 是打印模板
   
tplt = "{:4}\t{:8}\t{:16}"
   
# 打印表头
   
print(tplt.format("序号", "价格", "商品名称"))
   
count = 0
   
for g in ilt:
       
count = count + 1
       
print(tplt.format(count, g[0], g[1]))


# 定义主函数,记录程序运行整个过程
def main():
   
goods = "墨水"
   
# 爬取第一页和第二页,所以深度设为2
   
depth = 2
   
start_url = "http://s.taobao.com/search?q="+ goods
   
# 对输出变量定义一个变量
   
infoList = []
   
# 遍历页面信息,单独访问并处理每个页面
   
for i in range(depth):
       
# 使用try 对过程中发生的错误进行异常判断
       
try:
           
url = start_url + "&s="+ str(44*i)
           
html = getHTMLText(url)
            parsePage(infoList, html)
       
except:
           
continue
   
printGoodList(infoList)


main()

 

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值