【Python网络爬虫】前程无忧网爬虫+可视化
文章目录
- 前言
- 一、页面分析
- 二、代码实现
- 三、运行结果
- 四、数据统计及可视化
- 1.学历占比饼图
- 2.工作地点TOP10
- 3.福利词云
- 4.经验要求
- 5.公司性质占比圆环图
- 6.招聘人数玫瑰图
前言
本文以前程无忧网的爬虫职位为例,通过
面向对象
的形式进行编码,利用requests库
发起请求,利用xpath
与正则表达式
进行数据解析,将最终结果存入Excel
中,最后利用pyecharts
对数据进行统计并可视化(截图模糊但实际效果清晰)。
一、页面分析
首先进入前程无忧网首页:https://www.51job.com/
在搜索框中输入”爬虫“,点击搜索。
返回的页面如下。
通过在搜索框中搜索不同关键词,页面下方导航栏改变页数,以及选择不同城市,通过观察网页URL可以发现如下规律,由于URL的查询字符串部分完全一致,所以下图中未显示。(下图URL为全国爬虫职位第一页的URL)
下表为中国主要城市的编号。
城市名 | 城市编号 |
---|---|
全国 | 000000 |
北京市 | 010000 |
上海市 | 020000 |
广州市 | 030200 |
深圳市 | 040000 |
武汉市 | 180200 |
西安市 | 200200 |
杭州市 | 080200 |
南京市 | 070200 |
成都市 | 090200 |
重庆市 | 060000 |
东莞市 | 030800 |
大连市 | 230300 |
沈阳市 | 230200 |
苏州市 | 070300 |
昆明市 | 250200 |
长沙市 | 190200 |
合肥市 | 150200 |
宁波市 | 080300 |
郑州市 | 170200 |
天津市 | 050000 |
青岛市 | 120300 |
济南市 | 120200 |
哈尔滨市 | 220200 |
长春市 | 240200 |
福州市 | 110200 |
由于无法直接获得职位信息的总页数,所以只能通过尝试发现,全国爬虫职位信息共36页。同时职位编码可以利用程序进行转换。
通过以上分析可以得到模板URL,通过改变相应位置的参数即可改变搜索条件,其他位置的参数感兴趣的小伙伴可以自行研究。
到此网页的URL分析完成,下面解决数据提取问题。通过观察发现,服务器返回的网页源代码,与在开发者工具(F12)中的网页源代码不同,原因是由于浏览器呈现的数据是由JS通过浏览器二次渲染得到的,所以数据要在JS代码中获取。
经过xpath和正则表达式提取之后,可以看到数据的存储形式。每页返回一个列表,列表含有若干个下图所示的字典。这样就可以提取到想要的数据。
{"type":"engine_search_result","jt":"0_0","tags":[],"ad_track":"","jobid":"133748212","coid":"5719234","effect":"1","is_special_job":"","job_href":"https:\/\/jobs.51job.com\/shenzhen-ftq\/133748212.html?s=sou_sou_soulb&t=0_0","job_name":"爬虫工程师","job_title":"爬虫工程师","company_href":"https:\/\/jobs.51job.com\/all\/co5719234.html","company_name":"深圳中商产业研究院有限公司","providesalary_text":"1.5-2.5万\/月","workarea":"040100","workarea_text":"深圳-福田区","updatedate":"08-28","iscommunicate":"","companytype_text":"民营公司","degreefrom":"6","workyear":"5","issuedate":"2021-08-28 09:02:13","isFromXyz":"","isIntern":"","jobwelf":"五险一金 绩效奖金 全勤奖 员工旅游 节日福利","jobwelf_list":["五险一金","绩效奖金","全勤奖","员工旅游","节日福利"],"isdiffcity":"","attribute_text":["深圳-福田区","3-4年经验","本科","招1人"],"companysize_text":"50-150人","companyind_text":"专业服务(咨询、人力资源、财会)","adid":""},
二、代码实现
import urllib.parse
import random
import requests
from lxml import etree
import re
import json
import time
import xlwtclass QianChengWuYouSpider(object):# 初始化def __init__(self, city_id, job_type, pages):# url模板self.url = 'https://search.51job.com/list/{},000000,0000,00,9,99,{},2,{}.html'# UA池self.UApool = ["Mozilla/5.0 (Windows NT 6.0; rv:2.0) Gecko/20100101 Firefox/4.0 Opera 12.14","Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.0) Opera 12.14",'Mozilla/5.0 (Macintosh; Intel Mac OS X 10.9; rv:68.0) Gecko/20100101 Firefox/68.0','Mozilla/5.0 (Windows NT 6.1; WOW64; rv:75.0) Gecko/20100101 Firefox/75.0','Mozilla/5.0 (Macintosh; Intel Mac OS X 10.16; rv:83.0) Gecko/20100101 Firefox/83.0','Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.1; Trident/6.0; Touch; MASMJS)','Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 5.1; Trident/4.0; Hot Lingo 2.0)',"Opera/12.80 (Windows NT 5.1; U; en) Presto/2.10.289 Version/12.02","Opera/9.80 (Windows NT 6.1; U; es-ES) Presto/2.9.181 Version/12.00","Opera/9.80 (Windows NT 5.1; U; zh-sg) Presto/2.9.181 Version/12.00",]# 请求头self.headers = {'User-Agent': random.choice(self.UApool),# 注意加上自己的Cookie'Cookie': '',}# 请求参数self.params = {"lang": "c","postchannel": 0000,"workyear": 99,"cotype": 99,"degreefrom": 99,"jobterm": 99,"companysize": 99,"ord_field": 0,"dibiaoid": 0,"line": '',"welfare": ''}# 保存的文件名self.filename = "前程无忧网" + job_type + "职位信息.xls"# 城市编号self.city_id = city_id# 职位名称 【转为urlencode编码】self.job_type = urllib.parse.quote(job_type)# 页数self.pages = pages# 临时存储容器self.words = []# 请求网页def parse(self, url):response = requests.get(url=url, headers=self.headers, params=self.params)# 设置编码格式为gbkresponse.encoding = 'gbk'# 网页源代码return response.text# 数据提取def get_job(self, page_text):# xpathtree = etree.HTML(page_text)job_label = tree.xpath('//script[@type="text/javascript"]')[2].text# 正则表达式job_str = re.findall('"engine_jds":(.*"adid":""}]),', job_label)[0]# 转换为json类型data = json.loads(job_str)# 数据提取for item in data:# 职位名称job_name = item['job_name']# 职位链接job_href = item['job_href']# 公司名称company_name = item['company_name']# 公司链接company_href = item['company_href']# 月薪范围salary = item['providesalary_text']# 工作地点address = item['workarea_text']# 其他信息info_list = item['attribute_text']# 有个别数据不完整, 直接跳过if len(info_list) < 3:continue# 经验要求experience = info_list[1]# 学历要求education = info_list[2]# 发布日期update_date = item['updatedate']# 公司性质company_type = item['companytype_text']# 公司福利job_welf = item['jobwelf']# 公司行业company_status = item['companyind_text']# 公司规模company_size = item['companysize_text']self.words.append({"职位名称": job_name,"公司名称": company_name,"月薪范围": salary,"工作地点": address,"经验要求": experience,"学历要求": education,"发布日期": update_date,"公司性质": company_type,"公司福利": job_welf,"公司行业": company_status,"公司规模": company_size,"职位链接": job_href,"公司链接": company_href,})print("该页爬取完成")# 数据保存def save(self, words, filename, sheet_name='sheet1'):try:# 1、创建工作薄work_book = xlwt.Workbook(encoding='utf-8')# 2、创建sheet表单sheet = work_book.add_sheet(sheet_name)# 3、写表头head = []for k in words[0].keys():head.append(k)for i in range(len(head)):sheet.write(0, i, head[i])# 4、添加内容# 行号i = 1for item in words:for j in range(len(head)):sheet.write(i, j, item[head[j]])# 写完一行,将行号+1i += 1# 保存work_book.save(filename)print('数据保存成功')except Exception as e:print('数据保存失败', e)# 主程序def run(self):for page in range(1, self.pages + 1):# 拼接每页urlurl = self.url.format(self.city_id, self.job_type, page)# 请求网页page_text = self.parse(url)# 数据提取self.get_job(page_text)# 防止爬取过快time.sleep(random.randint(1, 2))self.save(words=self.words, filename=self.filename)if __name__ == '__main__':# 实例化爬虫对象 全国爬虫职位信息# city_id:城市编号(上表)# job_type:职位名称 (尽量精准,爬取到的数据会更贴切)# pages:页数(自己指定,注意不要超过总页数)spider = QianChengWuYouSpider(city_id=000000, job_type="爬虫", pages=20)# 运行主程序spider.run()
三、运行结果
四、数据统计及可视化
1.学历占比饼图
import pandas as pd
from pyecharts.charts import Pie
from pyecharts import options as optsdef education_analysis(data):# 统计每种学历的人数counts = data['学历要求'].value_counts()l1 = counts.index.tolist()l2 = counts.values.tolist()# 数据格式整理data_pair = [list(z) for z in zip(l1, l2)](# 设置图标背景颜色Pie(init_opts=opts.InitOpts(bg_color="rgba(206, 206, 206, 0.3)")).add(# 系列名称,即该饼图的名称series_name="学历分析",# 系列数据项data_pair=data_pair,# 饼图的半径,设置成默认百分比,相对于容器高宽中较小的一项radius="55%",# 饼图的圆心,第一项是相对于容器的宽度,第二项是相对于容器的高度center=["50%", "50%"],# 标签配置项label_opts=opts.LabelOpts(is_show=False, position="center"),)# 全局设置.set_global_opts(# 设置标题title_opts=opts.TitleOpts(# 名字title="学历占比分析",# 组件距离容器左侧的位置pos_left="center",# 组件距离容器上方的像素值pos_top="20",# 设置标题颜色title_textstyle_opts=opts.TextStyleOpts(color="#000"),),# 图例配置项,参数 是否显示图里组件legend_opts=opts.LegendOpts(is_show=True,# 竖向显示orient="vertical",# 距离左边5%pos_left="5%",# 距离上边60%pos_top="60%",),)# 系列设置.set_series_opts(tooltip_opts=opts.TooltipOpts(trigger="item", formatter="{a} <br/>{b}: {c} ({d}%)"),# 设置标签颜色label_opts=opts.LabelOpts(color="#000"),).render(path="./output/01-学历占比图.html"))if __name__ == '__main__':# 导入数据data = pd.read_excel('前程无忧网爬虫职位信息.xls')# 1.学历分析education_analysis(data)
由该饼图可以发现,公司要求本科学历达到将近60%,本科+中专达到近95%。可以看到爬虫这项技术相对简单,门槛较低。
2.工作地点TOP10
import pandas as pd
import re
from pyecharts.charts import Bar
from pyecharts import options as opts# 只保留城市名 不统计区
# 例:上海-徐汇区 -> 上海
def city_cleaning(df, loc):# 对指定列转化为列表数据original_data = df[loc].tolist()# 市与区之间以-分割current_data = []for item in original_data:division = re.sub("-.*", "", item)current_data.append(division)# pandas转化df_clean = pd.DataFrame(current_data, columns=[loc])return df_cleandef city_analysis(data):# 统计每个城市数量 取前十counts = data['工作地点'].value_counts()[:10]l1 = counts.index.tolist()l2 = counts.values.tolist()bar = (# 初始化Bar()# 添加横坐标.add_xaxis(l1)# 添加纵坐标.add_yaxis('数量', l2)# 将图形反转.reversal_axis()# 数值在图形右侧显示 left center right.set_series_opts(label_opts=opts.LabelOpts(position="right")).set_global_opts(# 图表标题title_opts=opts.TitleOpts(title="工作城市分析"),# y轴标签yaxis_opts=opts.AxisOpts(name="城市名"),# x轴标签xaxis_opts=opts.AxisOpts(name="数量"),))bar.render('./output/02-工作地点TOP10.html')if __name__ == '__main__':# 导入数据data = pd.read_excel('前程无忧网爬虫职位信息.xls')# 2.工作地点分析DATA = city_cleaning(data, "工作地点")city_analysis(DATA)
由该条形图可以发现,爬虫职位工作地点在北上广深居多,上海和深圳最多。
3.福利词云
import matplotlib.pyplot as plt
from wordcloud import WordCloud
import pandas as pddef word_cloud(data):# 删除缺失值complete_data = data.dropna()welf_list = complete_data['公司福利'].astype(str).tolist()text = ' '.join(welf_list)word_cloud = WordCloud(font_path="C:/Windows/Fonts/simfang.ttf",collocations=False,background_color='#fef8ef',scale=1.2,max_font_size=180,min_font_size=15).generate(text)plt.figure(figsize=(10, 10))plt.imshow(word_cloud, interpolation="bilinear")plt.axis("off")plt.savefig(r'./output/03-福利词云.png')plt.show()if __name__ == '__main__':# 导入数据data = pd.read_excel('前程无忧网爬虫职位信息.xls')# 3.福利词云word_cloud(data=data)
词频越大,该词在词云中越大。可以得知五险一金与效绩奖金为大多数公司都提供的福利。
4.经验要求
import pandas as pd
from pyecharts.charts import Bar
from pyecharts import options as optsdef experience_analysis(data):# 统计每种经验数量counts = data['经验要求'].value_counts()l1 = counts.index.tolist()l2 = counts.values.tolist()bar = (# 初始化Bar()# 添加横坐标.add_xaxis(l1)# 添加纵坐标.add_yaxis('数量', l2, category_gap="50%")# 数值在图形上侧显示 left center right.set_series_opts(label_opts=opts.LabelOpts(position="top")).set_global_opts(# 旋转x轴坐标 解决标签名字过长的问题xaxis_opts=opts.AxisOpts(axislabel_opts=opts.LabelOpts(rotate=-10), name="经验要求"),# 图表标题title_opts=opts.TitleOpts(title="经验要求分析"),# y轴标签yaxis_opts=opts.AxisOpts(name="数量"),))bar.render('./output/04-经验要求.html')if __name__ == '__main__':# 导入数据data = pd.read_excel('前程无忧网爬虫职位信息.xls')# 4.经验分析experience_analysis(data)
由图可以看到,爬虫职业要求1-4年经验居多,但无需经验与应届生也不在少数。
5.公司性质占比圆环图
import pandas as pd
from pyecharts.charts import Pie
from pyecharts import options as optsdef company_analysis(data):# 统计每种等级的人数counts = data['公司性质'].value_counts()# 等级l1 = counts.index.tolist()# 其对应人数l2 = counts.values.tolist()# 数据格式整理data_pair = [list(z) for z in zip(l1, l2)](Pie(init_opts=opts.InitOpts(bg_color="rgba(206, 206, 206, 0.3)")).add(series_name="公司性质分析",data_pair=data_pair,# 设置为圆环图radius=[80, 150],center=["50%", "50%"],label_opts=opts.LabelOpts(is_show=False, position="center"),).set_global_opts(title_opts=opts.TitleOpts(title="公司占比分析",pos_left="center",pos_top="20",title_textstyle_opts=opts.TextStyleOpts(color="#000"),),legend_opts=opts.LegendOpts(# 竖向显示orient="vertical",# 距离左边5%pos_left="5%",# 距离上边40%pos_top="40%",),).set_series_opts(tooltip_opts=opts.TooltipOpts(trigger="item", formatter="{a} <br/>{b}: {c} ({d}%)"),label_opts=opts.LabelOpts(color="#000"),).render(path="./output/05-公司性质占比.html"))if __name__ == '__main__':# 导入数据data = pd.read_excel('前程无忧网爬虫职位信息.xls')# 5.公司性质分析company_analysis(data)
民营公司与上市公司占近80%。
6.招聘人数玫瑰图
import pandas as pd
import re
from pyecharts.charts import Pie
from pyecharts import options as optsdef recruit_cleaning(df, loc):# 对指定列转化为列表数据original_data = df[loc].tolist()current_data = []for item in original_data:number = re.findall("招(.*)人", item)[0]if number == "若干":current_data.append("招若干人")else:number = int(number)if number >= 3 and number <= 10:current_data.append("招3-10人")elif number > 10:current_data.append("招10人以上")else:current_data.append("招{}人".format(number))# pandas转化df_clean = pd.DataFrame(current_data, columns=[loc])return df_cleandef recruit_analysis(data):# 统计招聘的人数counts = data['招聘人数'].value_counts()l1 = counts.index.tolist()l2 = counts.values.tolist()# 数据格式整理data_pair = [list(z) for z in zip(l1, l2)](Pie(init_opts=opts.InitOpts(bg_color="rgba(206, 206, 206, 0.3)")).add(series_name="招聘人数分析",data_pair=data_pair,# 设置为玫瑰图# radius:圆心角展示数据百分比,半径展示数据大小# area:圆心角相同,半径展示数据大小rosetype="radius",radius="55%",center=["50%", "50%"],label_opts=opts.LabelOpts(is_show=False, position="center"),).set_global_opts(title_opts=opts.TitleOpts(title="招聘人数占比分析",pos_left="center",pos_top="20",title_textstyle_opts=opts.TextStyleOpts(color="#000"),),legend_opts=opts.LegendOpts(# 竖向显示orient="vertical",# 距离左边5%pos_left="5%",# 距离上边70%pos_top="70%",),).set_series_opts(tooltip_opts=opts.TooltipOpts(trigger="item", formatter="{a} <br/>{b}: {c} ({d}%)"),label_opts=opts.LabelOpts(color="#000"),).render(path="./output/06-招聘人数占比.html"))if __name__ == '__main__':# 导入数据data = pd.read_excel('前程无忧网爬虫职位信息.xls')# 6.招聘分析df = recruit_cleaning(data, "招聘人数")recruit_analysis(data=df)
这招聘若干人就很灵性。
【Python网络爬虫】前程无忧网爬虫+可视化相关推荐
- 网络爬虫——前程无忧网数据获取及存储(高级)
网络爬虫--前程无忧网数据获取及存储(高级) 实验内容1 目标网站:前程无忧招聘网 目标网址:https://search.51job.com/list/120000,000000,0000,00,9 ...
- 网络爬虫——前程无忧网数据获取及存储
网络爬虫--前程无忧网数据获取及存储 目标网站:前程无忧招聘网 目标网址:https://search.51job.com/list/120000,000000,0000,00,9,99,Python ...
- python爬取前程无忧_用python爬取前程无忧网,看看我们是否真的“前程无忧”?...
The best time to plant a tree was 10 years ago,the second best time is now. 种一棵树最好的时间是十年前,其次是现在. 利用p ...
- 用python爬取前程无忧网,看看我们是否真的“前程无忧”?
作者:旧时晚风拂晓城 公众号:凹凸数据 The best time to plant a tree was 10 years ago,the second best time is now. 种一棵树 ...
- 可扩充的爬虫系统(新浪微博爬虫+QQ空间爬虫+全景网爬虫+环球网爬虫+新闻网爬虫)(图片爬虫系统)
源码日后博客分享 需求分析: 背景:机器视觉模型的训练需要大量的图像数据,而互联网上充斥着大量的图像数据,但是并不是所有数据能满足模型数据,这次我们需要满足人脸识别模型的要求,也就是需要大量含有人脸的 ...
- python网络爬图_Python爬虫爬图片需要什么
Python爬虫爬图片需要什么?下面用两种方法制作批量爬取网络图片的方法: 第一种方法:基于urllib实现 要点如下: 1.url_request = request.Request(url) 2. ...
- Python实战——斗图网爬虫
导入的包 request 一个很实用的python HTTP客户端库,编写爬虫和测试服务器响应数据时经常会用到 语法实例: import requestsr = requests.get('https ...
- python 中国裁决文书网 爬虫,完整版!!!
代码: import execjs import requests headers={"Accept":"*/*", "Accept-Encoding ...
- python爬取前程无忧_Python爬虫获取51job的51job代码,python,抓取,前程无忧
为了结果直观,做的简单 网页地址: https://search.51job.com/list/180200,000000,0000,00,9,99,%25E6%25AD%25A6%25E6%25B1 ...
最新文章
- 太拼了:谷歌第一编程语言小白也能学会!
- 速领!抗疫大礼包(含QQ音乐、全民K歌、网易云音乐等等)
- 最早的齿轮计算机,世界最古老“计算机”出土后110年,科学家终于解开它的秘密...
- 计算机进制简称,NO.A.0007——二进制;计算机容量单位B、KB、MB、GB和TB关系
- windows下使用net-snmp实现agent扩展(一)
- 光伏机器人最前线_高工机器人走进光伏:数字化车间未来可期
- AD19原理图背景栅格去掉(改为纯色)
- python3 _笨方法学Python_日记_DAY4
- vue项目使用阿里矢量图标库
- 【直播礼物特效】vapxtool简介(一)(企鹅电竞)
- 感谢所有的幸运与不幸 --- 致我的2016
- Tox21数据集学习笔记
- 出现 -2146959355, ‘服务器运行失败‘ 错误的处理
- Cannot deserialize instance of `com.xxx.project.biz.domain.xxx` out of START_ARRAY token;
- 不想周末被工作提醒打扰?你需要这个手机便签消息免打扰设置
- 创建一个Customer类,类中的属性有姓名(name)、年龄(age)、性别(gender),每一个属性分别有get/set方法。然后创建两个customer对象:张立、18、女和王猛、22、男。把
- 微信小程序操作es简单搜索
- 使用LaTeX输入矩阵
- 接口测试基础python+requests
- 2019年最新最全的医疗网站优化方案
热门文章
- 聊聊reactive streams的processors
- 携职教育:会计实操干货:10年老会计教你如何月末结转,收藏备用
- 计算机网络基础知识论文摘要,计算机网络基础知识论文大纲格式 计算机网络基础知识论文框架如何写...
- 大数据技术之Hadoop(Hadoop企业优化常见错误及解决方案)
- 一加手机,迟到的惊喜
- 电销机器人内置多套真人话术模板进行营销式会话
- 腾讯云年终选购云服务器攻略!
- 机器学习中的方差偏差分析(Bias-variance analysis)
- Python破解WIFI升级版保姆级教程,多线程破解+界面(附赠密码本)
- 智慧物流:RFID智能仓储管理解决方案-新导智能