初学Python之爬虫学习

为了满足自己的好奇心,想运用一下Python知识,然后和小伙伴要来了一个爬虫学习的B站博主的视频,教你学爬虫,真的很详细。


先上一个目录结构压压惊:
初学Python之爬虫学习_第1张图片
接下来就是贴代码笔记还有一个第三方库的目录:
初学Python之爬虫学习_第2张图片

1.requests的用法:

  • requests的基本使用
import requests

url = 'https://www.baidu.com'

res = requests.get(url=url)

#获取响应结果
print(res)
print(res.status_code)
print(res.content)
print(res.content.decode('utf-8'))
print(res.text)
print(res.url)
print(res.request.headers)
print(res.headers)
  • requests请求头
import requests

# 定义url
# url = 'https://www.lmonkey.com/'
url = 'https://www.xicidaili.com/nn'

#定义请求头信息  做个伪装身份
headers={
     
    'User-Agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.116 Safari/537.36'
}

#发起get请求
res = requests.get(url=url,headers=headers)
#获取响应状态码
code = res.status_code
print(code)
#响应成功后将响应内容写入文件中
if code == 200:
    with open('./text.html','w',encoding='utf-8') as fp:
        fp.write(res.text)
  • requests的post请求
import requests

url = 'https://fanyi.baidu.com/sug'

word = input('请输入要翻译的中文:')

headers = {
     

}

data = {
     
    'kw':word
}

res = requests.post(url=url,headers=headers,data=data)

code = res.status_code
print(code)
#返回的是文本数据
print(res.text)
#返回的是json数据
print(res.json())

if code ==200:
    print('请求成功')
    data = res.json()
    if data['errno'] == 0:
        print('响应成功')
        k = data['data'][0]['k']
        v = data['data'][0]['v'].split(';')[-2]
        print(k+'-->'+v)
  • requests的session方法
import requests

# 需要请求的目标地址
url = 'http://www.rrys2019.com/user/user'


# 登陆请求的地址
loginUrl = 'http://www.rrys2019.com/User/login/ajaxLogin'


#请求头
headers = {
     
    'User-Agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.116 Safari/537.36'
}


#如果需要爬虫程序主动记录cookie并且携带cookie 那么使用requests之前先调用session方法
#使用session方法返回的对象发送请求即可
req = requests.session()

#登陆请求时的数据
data = {
     
    'account' : '[email protected]',
    'password' : 'pyTHON123',
    'remeber' : '1',
    'url_back' : 'http://zmz2019.com/user/user'
}


#发起登陆请求
res = req.post(url=loginUrl,headers=headers,data=data)

#判断状态
code = res.status_code
print(code)

if code == 200:
    #发起新的请求,去获取目标数据
    res = req.get(url=url,headers=headers)
    with open('rr.html','w',encoding='utf-8') as fp:
        fp.write(res.text)

2.Xpath的使用

  • Xpath的基本操作
from lxml import etree

text ='''


	
		
		老白的登陆界面
		
	
	
		

账号:


密码:



'''
#第一种方法解析使用etree解析HTML字符串 html = etree.HTML(text) #print(html) #提取数据 r = html.xpath('/html/body/div/div/p/text()') #['账号:', '密码:'] print(r) #['账号:'] r = html.xpath('/html/body/div/div/p[1]/text()') print(r) #第二种方式读取一个HTML文件并解析 html = etree.parse('./test.html',etree.HTMLParser()) # print(html) # result = etree.tostring(html) # print(result.decode('utf-8')) #提取数据 r = html.xpath('/html/body/div/div/p/text()') print(r)
  • Xpath数据解析方法
from lxml import etree

#解析HTML文件
html = etree.parse('./test.html',etree.HTMLParser())

#提取数据
r = html.xpath('/html/body/div/div/p/text()')
print(r)
#双斜杠 这个查找方法可以找到所有P标签
r = html.xpath('//p/text()')
print(r)

#获取指定标签里面的 p 数据
r = html.xpath('//div[@class="bukuai"]/p/text()')
print(r)
#获取指定标签里面的 input 属性
r = html.xpath('//div[@class="bukuai"]/input/@value')
print(r)
#组合起来
t = html.xpath('//div[@class="teacher"]//li/a/text()')
h = html.xpath('//div[@class="teacher"]//li/a/@herf')
print(*zip(t,h))
res = list(zip(t,h))
print(res)

'''
/ 当前元素的直接子节点
// 当前元素的子节点或者子孙节点
text() 获取文本
@xxxx 获取对应属性的值
'''
  • Xpath实战登陆
#需求分析
import requests
from lxml import etree
#封装类进行学习猿地的登陆和订单获取
class LMonkey():
    #登陆路径的url
    loginurl = 'https://www.lmonkey.com/login'
    #账户中心地址URL
    orderurl = 'https://www.lmonkey.com/my/order'
    #请求头headers
    headers = {
     
        'User-Agent' : 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.116 Safari/537.36'
    }
    #请求对象
    req = None
    #token口令
    token = ''
    #订单号
    ordercode = 0
    #初始化方法
    def __init__(self):
        #请求对象的初始化
        self.req = requests.session()
        if self.getlogin():
            if self.postlogin():
                self.getorder()

    # 1.get 请求 login 页面, 设置cookie , 获取 _token
    #get 登陆页面 获取 _token
    def getlogin(self):
        res = self.req.get(url = self.loginurl,headers = self.headers)
        if res.status_code == 200:
            print('get登陆页面请求成功')
            html = etree.HTML(res.text)
            self.token = html.xpath('//input[@name="_token"]/@value')[0]
            print("token获取成功")
            return True
        else:
            print("请求错误")


    # 2.post请求 提交登陆数据,进行登录, 并且设置cookie
    #post 请求页面 设置cookie
    def postlogin(self):
        uname = input('手机号')
        passw = input('密码:')
        data={
     
            '_token':self.token,
            'username':uname,
            'password':passw
        }
        #发起post请求
        res = self.req.post(url=self.loginurl,headers=self.headers,data=data)
        if res.status_code == 200 or res.status_code == 302:
            print('登陆成功')
            # 请求订单数据
            return True
'''
17610195211
yichuan123
'''

    # 3.get请求,账号中心,获取默认订单号
    #get 请求账号中心 获取默认订单号
    def getorder(self):
        res = self.req.get(url=self.orderurl,headers=self.headers)
        if res.status_code == 200:
            print('账户中心请求成功,正在解析数据')
            html = etree.HTML(res.text)
            r = html.xpath('//div[@class="avatar-content"]//small/text()')
            print(r)
            self.ordercode = r


obj = LMonkey()

3.bs4的使用

  • bs4的基本操作_tag标签的获取
from bs4 import BeautifulSoup

html_doc = '''


	
		
		老白的登陆界面
		
	
	
		

账号:


密码:



'''
#创建一个 BeautifulSoup 对象 ,建议手动指定解析器 soup = BeautifulSoup(html_doc,'lxml') #1.通过 tag 标签对象获取文档数据 获取的是 第一个 r = soup.title print(r) #获取属性 p = soup.p['class'] print(p) #获取文本 p = soup.p.text print(p) # 2.通过搜索获取页面中的元素 find find_all # 查找所有p标签 r = soup.find_all('p') print(r) # 查找 指定内容 x = soup.find(id = 'link') z = soup.find(class_='inpu') print(x) print(z) # 获取可见的文本内容 r = soup.find('title') r = r.get_text() print(r) #3.css选择器 #通过标签 选择元素 r = soup.select('title') print(r) #通过class 类名获取元素 r = soup.select('.inpu') print(r) #通过ID名获取元素 r = soup.select('#inpu') print(r) #通过空格 层级关系获取元素 r = soup.select('html body input') print(r) #通过逗号,并列关系获取元素 r = soup.select('p,input') print(r)
  • bs4实战_学习猿地_猿圈
from bs4 import BeautifulSoup
import requests,json
'''
分析爬取的数据
数据源地址:https://www.lmonkey.com/t
数据内容:文章标题, 文章的链接, 作者, 发布时间
工具:
    python, requests, bs4, json
'''
#1.定义请求的URL和请求头
url = 'https://www.lmonkey.com/t'
headers = {
     
    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.116 Safari/537.36'
}

#2.发送请求
res = requests.get(url=url,headers=headers)

#3.检测请求是否成功并获取请求的源代码(源数据)
if res.status_code == 200:
    #4.解析数据
    soup = BeautifulSoup(res.text,'lxml')
    #获取页面中所有的文章大列表
    divs = soup.find_all('div',class_="list-group-item list-group-item-action p-06")
    varlist = []
    for i in divs:
        r = i.find('div',class_="topic_title")
        if r:
            vardict = {
     
                'title':r.text.split('\n')[0],#解决换行问题
                'url':i.a['href'],
                'author':i.strong.a.text,
                'pubdate':i.span['title']
            }
            varlist.append(vardict)
    print(varlist)
    #5.写入数据
    with open('./yq.json','w') as fp:
        json.dump(varlist,fp)
  • bs4实战_学习猿地_猿圈_优化
from bs4 import BeautifulSoup
import requests,json
'''
分析爬取的数据
数据源地址:https://www.lmokey.com/t
数据内容:文章标题, 文章的链接, 作者, 发布时间
工具:
    python, requests, bs4, json
'''

#封装类
class Bs4Yq():
    #定义属性
    #请求的url
    url = 'https://www.lmonkey.com/t'
    #请求头
    headers = {
     
        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.116 Safari/537.36'
    }
    #响应源代码的存放位置
    res_html = None

    #存储解析后的数据
    varlist = []

    #初始化方法
    def __init__(self):
        #发起一个请求
        res = requests.get(url=self.url,headers=self.headers)
        if res.status_code == 200 :
            print('请求成功')
            self.res_html = res
            if self.ParseData():
                self.WriteJson()
                print('写入成功')
        else:
            print('请求失败')


    #解析html数据
    def ParseData(self):
        soup = BeautifulSoup(self.res_html.text, 'lxml')
        try:
            # 获取页面中所有的文章大列表
            divs = soup.find_all('div', class_="list-group-item list-group-item-action p-06")
            varlist = []
            for i in divs:
                r = i.find('div', class_="topic_title")
                if r:
                    vardict = {
     
                        'title': r.text.split('\n')[0],  # 解决换行问题
                        'url': i.a['href'],
                        'author': i.strong.a.text,
                        'pubdate': i.span['title']
                    }
                    self.varlist.append(vardict)
            return True
        except:
            return False

    #写入json数据
    def WriteJson(self):
        if self.varlist !=[]:
            try:
                with open('./yq1.json', 'w') as fp:
                    json.dump(self.varlist, fp)
                return True
            except:
                return False
        else:
            print('无法获取当前解析的数据')
            return False


res = Bs4Yq()
print(res)

4.re模块的使用 也就是正则表达式

  • re正则模块基本使用
import re
'''
正则表达式,就是使用普通字符,转义字符,特殊字符组成一个规则
使用这个规则对文本的内容完成一个搜索或匹配或替换的功能

正则表达式的组成
    普通字符:大小写字母,数字,符号...
    转义字符:\w \W \d \D \s \S ...
    特殊字符:. * ? + ^ $ [] {} ()
    匹配模式:I U ...
'''
#使用正则表达式进行匹配的 基本语法
#定义字符串
vars = 'iloveyou521tosimida'
#定义正则表达式
reg = '\d'
#调用正则函数方法
res = re.findall(reg,vars)
print(res)
#返回的是一个 迭代器
res = re.finditer(reg,vars)
for i in res:
    print(i)


vars = 'xyz'
reg = '^xy[a-z]?z'
print(re.search(reg,vars))
  • re正则表达式的定义和规则
# 正则表达式的规则和定义
import re

#1.普通字符
vars = 'iloveyou'
reg = 'love'
res = re.search(reg,vars).group()
print(res)

#2.转义字符 \w \W \d \D \s \S ...
varstr = 'ilove521you'
reg = '\d' #单个数字
res = re.search(reg,varstr)
print(res)
reg = '\D' #单个非数字
res = re.search(reg,varstr)
print(res)
reg = '\w' #单个字母,数字 下划线
res = re.search(reg,varstr)
print(res)
reg = '\W' #代表单个非字母,非数字,非下划线
res = re.search(reg,varstr)
print(res)
reg = '\s' #单个的 空格符或者制表符
res = re.search(reg,varstr)
print(res)
reg = '\S' #单个的 非空格符或者非制表符
res = re.search(reg,varstr)
print(res)

#3.特殊字符 . * + ? 【】 {} () ^ $
varstr = 'hello world 5211 iloveyou'
reg = '.'     # 点 . 代表 单个的 任意字符 除了换行符
res = re.search(reg,varstr).group()
print(res,len(res))
reg = '.*'    #  * 匹配次数 任意次数 特点:如果使用* 号,那么在匹配的开始处如果符合要求,则按照规则一直向后匹配,知道不符合规则并结束,并把前面符合的数据返回;如果再匹配的开始处就不符合要求,就返回空
res = re.search(reg,varstr).group()
print(res,len(res))
reg = '\w+'   # + 至少要匹配一次
res = re.search(reg,varstr).group()
print(res,len(res))
reg = '\w+?'  # ? 拒绝贪婪,就是前面的匹配规则只要达成则返回
res = re.search(reg,varstr).group()
print(res,len(res))
reg = '\w{4}' # {}表示匹配次数 ,{4}表示必须匹配四次
res = re.search(reg,varstr).group()
print(res,len(res))
reg = '\w{2,5}' # {}表示匹配次数 ,{2,5}表示必须匹配2次到5次
res = re.search(reg,varstr).group()
print(res,len(res))
reg = '[a-z,A-Z,0-9,_]' # [] 表示字符的一个范围,[a-z,A-Z,0-9,_] == \w
res = re.search(reg,varstr).group()
print(res,len(res))
varstr = 'hello WORLD iloveyou5211'
reg = '\w+(\d{4})' # ()代表子组,括号中的表达式首先作为整个正则的一部分,另外会把符合小括号中的内容单独提取一份
res = re.search(reg,varstr)
print(res.group())
print(res.groups())

varstr = '17610105211'
#定义一个正则表达式的规则  匹配手机号的正则表达式
reg = '^1\d{10}$' # ^ 代表开头   $ 代表结尾
res = re.search(reg,varstr)
print(res.group())

#4.正则模式
varstr = 'iLOVEyou'
reg = '[a-z]+'
res = re.search(reg,varstr,re.I) # re.I 不区分大小写
print(res)

  • re模块相关函数
#re模块相关函数
'''
re.match()函数
    + 从头开始匹配
    + 要么第一个符合要求,要么不符合
    + 匹配成功则返回Match对象,否则返回None
    + 返回的结果可以使用group()方法获取返回的值
    + 返回的结果可以使用span()方法获取返回的值的下标范围区间
re.search()
    + 从字符串开头结尾开始搜索式匹配
    + 匹配成功则返回Match对象,否则返回None
    + 返回的结果可以使用group()方法获取返回的值
    + 返回的结果可以使用span()方法获取返回的值的下标范围区间

search() 和 match() 方法的区别:
    match()方法是从字符串的开头进行匹配,如果开始就不符合正则的要求,则匹配失败,返回None
    search()方法是从字符串的开始位置一直搜索到字符串的最后,如果在整个字符串中都没有匹配到,则失败,返回None

re.findall()
re.finditer()
re.sub()


'''
import re
vars = 'iloveyou521tosimida'
reg = 'love'
#调用 match()方法
res = re.match(reg,vars)
print(res)
reg = 'ilove'
res = re.match(reg,vars)
print(res)
print(res.group())
print(res.span())
#调用 search() 方法
vars = 'iloveyou521tosimida'
reg = 'love'
res = re.search(reg,vars)
print(res)
print(res.group())
print(res.span())
  • re模块相关函数_其他函数
'''
re.findall()
    + 按照正则表达式的规则在字符中匹配所有符合规则的元素,结果返回一个列表,如果没有找到则返回空列表


re.finditer()
    + 按照正则表达式的规则在字符中匹配所有符合规则的元素,返回一个迭代器

re.sub()
    + 搜索替换
    + 按照正则表达式的规则在字符中找到需要被替换的字符串,完成一个替换
    + 参数要求:
        - pattern:正则表达式的规则,匹配需要被替换的字符串
        - repl:替换后的字符串
        - string:被替换的原始字符串

compile()
    可以直接将正则表达式定义为 正则对象,使用正则对象直接操作

'''
import re

varstr = 'iloveyou521tosimida511'

reg = '\d'
res = re.findall(reg,varstr)
print(res)

reg = '\d{3}'
res = re.findall(reg,varstr)
print(res)

res = re.finditer(reg,varstr)
print(list(res))
print(res)

res = re.sub(reg,'AAA',varstr)
print(res)

reg = re.compile('\d{3}')
res = reg.findall(string=varstr)
print(res)
lines = [
    'i love 512 you',
    'i love 521 you',
    'i love 345 you',
    'i love 543 you',\
]
for i in lines:
    res = reg.search(i)
    print(res.group())

  • re正则实战_猿来如此
'''

数据地址: https://www.lmonkey.com/ask
数据字段: 问题 时间 作者 url链接

'''
import json
import re
import requests

# 1. 定义请求url 请求头

url = 'https://www.lmonkey.com/ask'
headers = {
     
    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.116 Safari/537.36'
}

# 2.发起请求
res = requests.get(url=url,headers=headers)

#3.检测请求是否成功
if res.status_code == 200:
    #4.获取返回的数据
    res_html = res.text
    with open('./res.html','w',encoding='utf-8') as fp:
        fp.write(res_html)
    #5.进行数据解析

    #定义解析 问题标题的正则
    reg = '
(.*?) titlelist_arr = re.findall(reg,res_html) # print(titlelist_arr,len(titlelist_arr)) #定义解析 作者的正则 reg = '(.*?)' author_list = re.findall(reg,res_html) # print(author_list,len(author_list)) #定义解析 时间的正则 reg = '' time_list = re.findall(reg, res_html) # print(time_list,len(time_list)) #定义解析 链接的正则 reg = '' href_list = re.findall(reg, res_html) # print(href_list,len(href_list)) data = list(zip(titlelist_arr,author_list,time_list,href_list)) #列表推导式 datalist = [{ 'title':i[0],'author':i[1],'datetime':i[2],'url':i[3]} for i in data] print(datalist) #数据入库 with open('./data.json','w',encoding='utf-8') as fp: json.dump(datalist,fp) ''' #常规方式处理数据 datalist = [] for i in data: res = { 'title':i[0], 'author':i[1], 'datetime':i[2], 'url':i[3] } datalist.append(res) print(datalist) '''

以上就是跟着那位博主学习的爬虫知识,学习爬虫后要多加练习,建议自己写一个前端代码然后自己爬,自己写自己爬,希望这些代码对你有用,如果没用,那去看那位博主的教学吧~

你可能感兴趣的:(Python)