下文流程图概括了「数据清洗」与「多维度分析」两条主链路。
graph TD
A[原始招聘数据] --> B[空值清洗]
B --> C[去重处理]
C --> D[地域筛选]
D --> E[职位关键词过滤]
E --> F[清洗后数据视图]
F --> G[市场需求分析]
F --> H[薪资分析]
F --> I[技能需求分析]
G --> G1[城市招聘量]
G --> G2[企业类型分布]
G --> G3[职位数目统计]
H --> H1[薪资分布]
H --> H2[工作年限与薪资]
H --> H3[企业类型与薪资]
I --> I1[技能词频统计]
I --> I2[核心技能TOP30]
J[游戏岗位数据] --> K[对比分析]
L[运维岗位数据] --> K
F --> K
K --> M[可视化图表]
项目概述
本项目承担「招聘数据采集 → 多层视图清洗 → 薪资标准化 → 多维度统计分析 → 可视化呈现」的完整链路,在本项目中负责数据清洗逻辑设计与 SQL 分析开发。
技术栈:MySQL 8+ 作为主数据库,使用窗口函数(ROW_NUMBER)进行去重,视图(View)实现分层数据清洗,CASE 表达式完成薪资单位标准化,字符串函数提取薪资数值,聚合函数与分组统计实现多维度分析。分析结果导出至 Excel 进行可视化呈现。数据来源为招聘网站爬取的原始数据,包含数据分析、游戏、运维三类岗位。
| 类别 | 技术选型 | 用途 |
|---|---|---|
| 数据库 | MySQL 8+ | 数据存储与 SQL 分析,支持窗口函数 |
| 数据清洗 | SQL 视图(View) | 分层清洗,空值过滤、去重、地域筛选、关键词过滤 |
| 数据转换 | CASE 表达式 + 字符串函数 | 薪资单位标准化,提取最小/最大/平均薪资 |
| 统计分析 | 聚合函数 + GROUP BY | 市场需求、薪资分布、技能词频统计 |
| 可视化 | Excel | 图表制作与数据呈现 |
| 原始数据 | 7z 压缩包 | 招聘网站爬取的原始数据存储 |
项目背景
对于有意进入数据分析领域的求职者而言,了解市场需求、薪资水平和技能要求至关重要。然而,招聘网站上的信息分散且格式不统一:薪资表述方式多样(千/月、万/月、万/年),职位名称存在大量噪声,同一公司可能重复发布相同职位。若不进行系统化清洗与分析,难以获得准确的行业洞察。
本项目旨在通过 SQL 完成数据清洗与多维度分析,回答以下核心问题:哪些城市的数据分析岗位需求最大?不同企业类型的薪资水平如何?工作年限与薪资增长的关系如何?求职者需要掌握哪些核心技能?同时,引入游戏岗位和运维岗位作为参照,帮助求职者做出更明智的职业选择。
系统架构与选型
采用分层视图架构:原始数据经多层视图逐步清洗,每层视图解决一类数据质量问题。第一层过滤空值与 NULL,第二层使用窗口函数去除重复职位(同公司同职位保留最新发布),第三层筛选一线城市(北京、上海、广州、深圳),第四层通过关键词过滤确保职位相关性。清洗后的数据视图作为分析基础,支撑市场需求、薪资分布、技能需求三大分析维度。
选型考量:MySQL 8+ 支持窗口函数,可简洁实现「同公司同职位保留最新」的去重逻辑;视图机制使清洗步骤可复用、可审计,便于调试与维护;CASE 表达式配合字符串函数可灵活处理薪资格式差异。整体方案无需引入额外工具,纯 SQL 即可完成从清洗到分析的全流程。
关键技术选型理由
-
MySQL 窗口函数(ROW_NUMBER)
用于实现「同公司同职位按发布时间排序,仅保留最新一条」的去重逻辑。相比传统的子查询或自连接,窗口函数语义更清晰、性能更优,且便于扩展(如保留前 N 条)。
-
视图(View)分层架构
将清洗步骤拆分为多个视图(v_data_clean_null → v_clean_data_distinct → v_data_clean_workplace → v_data_clean_jobname → v_data_clean),每个视图解决一类问题。分层设计便于定位问题、独立测试,且上层分析逻辑无需关心清洗细节。
-
CASE 表达式 + 字符串函数
招聘数据中薪资格式多样(「8-15千/月」「2-3万/月」「20-30万/年」),使用 CASE 表达式将单位统一为「元/月」,再用 SUBSTRING_INDEX 提取最小值与最大值,最终计算平均薪资。该方案完全在 SQL 层完成,无需外部脚本。
功能模块
数据清洗
系统提供四层清洗机制,确保分析数据的质量与相关性:
- 空值过滤:剔除任意关键字段为空或 NULL 的记录,包括职位链接、职位名称、公司名称、薪资、工作地点、企业类型、学历要求、工作年限、发布日期、职位详情等
- 去重处理:使用
ROW_NUMBER() OVER (PARTITION BY company_name, job_name ORDER BY issuedate DESC)按公司和职位分组,仅保留最新发布的记录 - 地域筛选:仅保留北京、上海、广州、深圳四个一线城市的数据,确保区域代表性
- 关键词过滤:职位名称必须包含「数据」关键词,过滤公关、销售等无关职位
清洗效果:
- 原始数据量:约 8 万条
- 清洗后数据量:约 5,400 条
- 过滤率:约 93%
薪资标准化
招聘数据中薪资表述格式多样,需统一为可比较的数值:
薪资格式处理:
- 「千/月」→ 乘以 1,000
- 「万/月」→ 乘以 10,000
- 「万/年」→ 乘以 833(折算为月薪)
薪资提取流程:
- 使用 CASE 表达式识别薪资单位
- 使用
SUBSTRING_INDEX提取薪资范围的最小值与最大值 - 计算平均薪资
(salary_min + salary_max) / 2
市场需求分析
从多个维度分析数据分析岗位的市场需求:
分析维度:
- 城市招聘量与职位数目
- 企业类型分布(民营、国企、外资、合资等)
- 招聘量占比统计
核心发现:
- 数据分析岗位总招聘量约 4 万人
- 北京是需求最大的城市
- 民营企业对数据分析人才需求最高
薪资分布分析
从多个维度分析薪资水平与增长趋势:
分析维度:
- 薪资区间分布(按 5K/10K/20K/30K/40K/50K 分段)
- 工作年限与平均薪资的关系
- 不同企业类型的平均薪资对比
核心发现:
- 数据分析岗位高薪比例较高,低薪比例较小
- 工作第 5 年薪资可翻倍,7 年后可达初始薪资的 3 倍
- 不同企业类型的薪资分布较为均匀
技能需求分析
通过职位详情的关键词匹配,统计技能需求频率:
分析方法:
- 使用预定义的技能关键词表(skill_table)
- 通过
LIKE CONCAT('%', skill, '%')匹配职位详情 - 按出现频率排序,取 TOP 30 核心技能
核心发现:
- SQL、大数据、EXCEL、报表、Python 是最核心的技能要求
- 金融和电商领域的项目经验较为重要
对比分析
引入游戏岗位和运维岗位作为参照组,使用相同的清洗与分析流程:
- 游戏岗位:职位名称包含「游戏」关键词
- 运维岗位:职位名称包含「运维」关键词
通过对比,帮助求职者了解数据分析岗位在市场需求、薪资水平、技能要求等方面的相对优势。
技术难点与实现
薪资格式多样性处理
难点:招聘数据中薪资表述格式不统一,包括「8-15千/月」「2-3万/月」「20-30万/年」等多种形式,直接比较或统计会产生错误结果。
方案:设计两阶段处理流程。第一阶段使用 CASE 表达式识别单位并转换为统一系数(千/月→1000,万/月→10000,万/年→833);第二阶段使用 SUBSTRING_INDEX 嵌套调用提取薪资范围,先截取单位前的数值部分,再按「-」分隔提取最小值与最大值。最终计算平均薪资,实现所有薪资数据的可比较性。
高效去重逻辑
难点:同一公司可能多次发布相同职位,导致数据重复;传统的 DISTINCT 或 GROUP BY 无法保留最新发布的完整记录。
方案:使用 MySQL 8+ 的窗口函数 ROW_NUMBER() OVER (PARTITION BY company_name, job_name ORDER BY issuedate DESC),为每组(公司+职位)的记录按发布时间降序编号,仅保留编号为 1 的记录。该方案语义清晰,且保留了完整的记录信息,便于后续分析。
技能词频统计
难点:职位详情为非结构化文本,需从中提取技能关键词并统计频率;直接使用正则或分词工具会增加复杂度。
方案:预先构建技能关键词表(skill_table),使用 INNER JOIN 配合 LIKE CONCAT('%', skill, '%') 进行模糊匹配。该方案充分利用 SQL 的集合运算能力,无需引入外部文本处理工具,且技能表可灵活扩展。通过 GROUP BY 和 COUNT 统计各技能的出现频率,取 TOP 30 作为核心技能。
总结
本项目通过纯 SQL 实现了招聘数据的完整分析链路:从原始数据的多层清洗(空值过滤、去重、地域筛选、关键词过滤),到薪资格式标准化,再到市场需求、薪资分布、技能需求的多维度统计分析。分层视图架构使清洗逻辑可复用、可审计,窗口函数简化了去重逻辑,CASE 表达式与字符串函数的组合解决了薪资格式多样性问题。
分析结果表明:数据分析岗位市场需求旺盛(约 4 万人),薪资水平可观(高薪比例高、增长稳定),核心技能以 SQL、大数据、EXCEL、Python 为主。后续可扩展方向包括:引入更多城市与行业维度、增加时间序列分析(招聘趋势)、使用 Python/Pandas 实现更复杂的可视化与预测分析。