Python实战:百度指数数据抓取、清洗与趋势分析全流程

发布时间:2026/10/22 3:17:31

Python实战:百度指数数据抓取、清洗与趋势分析全流程 简介这份Python完整示例代码面向具备基础语法、希望入门数据分析的开发者围绕百度指数这一关键词热度工具演示从数据获取到可视化呈现的完整流程。包内共6个文件以2个py脚本为核心配合1个csv数据文件、1个txt城市代码、1个docx关键词说明及1个docx文档压缩包约24KB结构轻量便于快速上手。代码示例串联Pandas、NumPy、Matplotlib与requests等常用库覆盖API请求、DataFrame清洗、日期转换、均值统计及时间序列绘图等环节并涉及缺失值与异常值处理思路。已有700人学习下载适合想借真实场景熟悉数据分析链路、对照脚本动手实践的读者参考。1. 百度指数数据分析python完整示例代码从数据获取到趋势洞察的落地路径百度指数反映的是关键词在百度搜索中的日均搜索量趋势对做市场分析、内容运营、SEO 优化的人来说它是一份低成本、高频次的需求侧数据。但很多人卡在第一步指数页面只给图表不给原始数据。手动抄几十个关键词、几百天跨度抄到怀疑人生。用 Python 把这条链路跑通就能把“看趋势”变成“算趋势”——批量拉取、清洗、对齐、可视化、导出一套脚本管到底。这篇笔记面向有基础 Python 能力、想用代码替代手工取数的从业者从零搭出一个可复现的百度指数数据分析流程。需要说明的是百度指数没有公开的官方数据接口常见做法是通过浏览器开发者工具观察页面加载时的请求规律再用脚本模拟这些请求获取数据。下面所有代码都围绕这个思路展开你可以直接抄作业也可以按自己的场景改参数。2. 环境准备与请求链路拆解先把“黑匣子”打开2.1 为什么不能直接 requests.get 就完事百度指数的数据加载不是简单的静态页面。你在浏览器里打开指数页面看到的曲线是前端 JavaScript 拿到数据后渲染出来的。数据本身通过异步请求返回请求里带着几个关键参数关键词、时间范围、以及一个由前端生成的加密签名。这个签名是最大的门槛——它随时间变化直接复制粘贴只能管几分钟。常见做法是用自动化浏览器工具比如 Playwright 或 Selenium打开页面让页面自己完成签名计算然后拦截网络请求把返回的 JSON 数据截下来。这样就不需要逆向签名算法稳定性也更好。我一般会优先选 Playwright因为它对异步请求的拦截更干净而且自带等待机制不容易翻车。2.2 最小可运行环境与依赖安装先建一个干净的虚拟环境避免和系统里其他包的版本打架。Python 版本建议 3.9 以上3.11 更稳。python -m venv venv source venv/bin/activate # Windows 用 venv\Scripts\activate pip install playwright pandas matplotlib openpyxl playwright install chromium这里装了五个东西playwright 负责驱动浏览器pandas 做数据清洗和透视matplotlib 画图openpyxl 用来导出 Excel。playwright install chromium是下载浏览器内核只跑一次就行。如果你之前装过 Selenium也不用卸两者互不冲突但建议只保留一套减少排查成本。2.3 拦截请求拿到第一份原始 JSON下面这段代码打开百度指数首页输入关键词等待图表加载然后监听所有返回 JSON 的响应。关键点是page.on(response, ...)这个回调它会在每个响应到达时触发。from playwright.sync_api import sync_playwright import json def fetch_index_data(keyword: str, start_date: str, end_date: str): with sync_playwright() as p: browser p.chromium.launch(headlessFalse) # 首次调试建议有头 page browser.new_page() captured [] def on_response(response): # 只关心返回 JSON 且 URL 里带 index 的请求 if application/json in response.headers.get(content-type, ): if index in response.url or api in response.url: try: captured.append(response.json()) except Exception: pass page.on(response, on_response) # 打开指数页面关键词通过 URL 参数传入 url fhttps://index.baidu.com/v2/main/index.html#/trend/{keyword}?words{keyword} page.goto(url, wait_untilnetworkidle) # 设置时间范围这里用页面上的日期控件具体选择器需按实际页面调整 page.wait_for_timeout(3000) # 等图表渲染 browser.close() return captured if __name__ __main__: data fetch_index_data(Python, 2024-01-01, 2024-06-30) print(json.dumps(data, ensure_asciiFalse, indent2)[:2000])逻辑说明headlessFalse是为了第一次跑的时候能看到浏览器在干什么方便判断是否被拦截。wait_untilnetworkidle表示等网络请求基本停了再继续但百度指数有轮询可能永远不 idle所以后面加了固定等待。captured列表会收集所有符合条件的 JSON实际返回的可能有多个需要根据结构判断哪个是趋势数据。参数说明keyword就是你要查的词中文也行但 URL 里要做编码。start_date和end_date目前没直接用到因为页面上的时间选择需要模拟点击更稳的做法是直接在拦截到的请求里改参数重放。这个后面会讲。提示第一次跑建议把headless设为False观察页面是否正常加载。如果出现验证码说明请求频率过高需要降低速度或换时间段。3. 数据清洗与结构化把 JSON 变成 DataFrame3.1 识别有效数据体别把广告 JSON 也收进来拦截到的 JSON 可能包含页面配置、用户信息、广告位数据。真正的指数数据通常有几个特征包含data字段里面是userIndexes或index数组数组元素有date和value。我一般会写一个过滤函数只保留符合这个结构的响应。def extract_trend_json(captured_list): 从拦截到的多个 JSON 中找出趋势数据 for item in captured_list: if not isinstance(item, dict): continue # 常见结构{data: {userIndexes: [{date: ..., value: ...}]}} data item.get(data) if isinstance(data, dict): for key in [userIndexes, index, trend]: if key in data and isinstance(data[key], list): return data[key] # 有些版本直接返回数组 if isinstance(data, list) and len(data) 0: if date in data[0] and value in data[0]: return data return None这段代码不依赖固定字段名而是按“有没有 date 和 value”来判断兼容性更好。如果你拿到的数据里 value 是加密字符串那说明签名没对上需要回到上一步检查请求是否完整。3.2 构建 DataFrame 并处理缺失值拿到列表后直接转成 DataFrame然后做三件事日期解析、数值转换、缺失值填充。import pandas as pd def build_dataframe(trend_list): df pd.DataFrame(trend_list) df[date] pd.to_datetime(df[date]) df[value] pd.to_numeric(df[value], errorscoerce) df df.sort_values(date).reset_index(dropTrue) # 指数数据常见缺失周末或节假日可能为空用前值填充 df[value] df[value].fillna(methodffill).fillna(0) # 加上移动平均方便看趋势 df[ma7] df[value].rolling(window7, min_periods1).mean() df[ma30] df[value].rolling(window30, min_periods1).mean() return dferrorscoerce会把无法转换的值变成 NaN避免整列报错。ffill是前向填充适合指数这种连续但偶尔缺失的场景。移动平均的窗口 7 和 30 是经验值7 天对应一周周期30 天对应月度趋势。如果你分析的是短期活动可以把 7 改成 3。3.3 多关键词对齐时间轴不一致怎么办同时分析多个词时每个词返回的日期范围可能略有差异。用pd.merge按日期做外连接再统一填充。def merge_keywords(df_dict): df_dict: {Python: df1, Java: df2} merged None for kw, df in df_dict.items(): temp df[[date, value]].rename(columns{value: kw}) if merged is None: merged temp else: merged pd.merge(merged, temp, ondate, howouter) merged merged.sort_values(date).reset_index(dropTrue) merged merged.fillna(methodffill).fillna(0) return merged这样得到的表每一列是一个关键词每一行是一个日期。后续画图、算相关性都方便。注意howouter会保留所有日期如果某个词缺某天数据填充后可能引入偏差所以最好在填充前先检查缺失比例超过 20% 的词建议单独处理。4. 可视化与趋势解读让图表说人话4.1 单关键词趋势图把移动平均叠上去import matplotlib.pyplot as plt import matplotlib.dates as mdates plt.rcParams[font.sans-serif] [SimHei] # 中文显示 plt.rcParams[axes.unicode_minus] False def plot_single(df, keyword): fig, ax plt.subplots(figsize(12, 5)) ax.plot(df[date], df[value], alpha0.3, label日指数, colorgray) ax.plot(df[date], df[ma7], label7日均线, colororange, linewidth2) ax.plot(df[date], df[ma30], label30日均线, colorred, linewidth2) ax.xaxis.set_major_formatter(mdates.DateFormatter(%m-%d)) ax.xaxis.set_major_locator(mdates.WeekdayLocator(interval2)) plt.xticks(rotation45) ax.set_title(f{keyword} 百度指数趋势) ax.legend() plt.tight_layout() plt.savefig(f{keyword}_trend.png, dpi150) plt.show()灰色细线是原始日指数波动大但能看到突发峰值。橙色 7 日均线抹平了周内波动红色 30 日均线看月度走向。如果 7 日均线突然上穿 30 日均线通常意味着热度在爬升。保存图片时 dpi 设 150够清晰又不至于文件太大。4.2 多关键词对比归一化后再比不同词的指数绝对值差异可能很大直接画在一起小的那条会被压成直线。常见做法是做归一化把每个词的值除以自己的最大值变成 0 到 1 之间的相对趋势。def plot_compare(merged_df, keywords): fig, ax plt.subplots(figsize(12, 5)) for kw in keywords: normalized merged_df[kw] / merged_df[kw].max() ax.plot(merged_df[date], normalized, labelkw, linewidth2) ax.xaxis.set_major_formatter(mdates.DateFormatter(%m-%d)) plt.xticks(rotation45) ax.set_ylabel(相对热度归一化) ax.set_title(关键词热度对比) ax.legend() plt.tight_layout() plt.savefig(compare_trend.png, dpi150) plt.show()归一化后你比较的是“走势形状”而不是“绝对量级”。如果两个词走势高度重合说明它们可能受同一事件驱动如果一个词先涨、另一个滞后涨可能存在传导关系。这个技巧在选品和舆情分析里很实用。4.3 导出 Excel给不写代码的同事留条路分析结果最终要给别人看Excel 是最通用的格式。pandas 的to_excel可以一次写多个 sheet。def export_excel(merged_df, single_dfs, filenamebaidu_index.xlsx): with pd.ExcelWriter(filename, engineopenpyxl) as writer: merged_df.to_excel(writer, sheet_name多词对比, indexFalse) for kw, df in single_dfs.items(): df.to_excel(writer, sheet_namekw[:20], indexFalse) # sheet 名有长度限制 print(f已导出{filename})sheet 名超过 31 个字符会报错所以做了截断。如果关键词里有特殊字符比如*、?也要替换掉否则 openpyxl 会抛异常。导出后建议手动打开检查一下日期列格式有时候 Excel 会自动把日期识别成数字需要设置单元格格式。5. 避坑与常见问题那些让我熬夜的瞬间5.1 请求返回 403 或验证码现象脚本跑几次后页面跳转到验证页或者接口返回 403。原因请求频率过高或者浏览器指纹被识别。解决降低速度每次请求间隔 5 到 10 秒用headlessFalse加随机延迟如果持续被封换 IP 或等几小时再试。我一般会在脚本里加page.wait_for_timeout(random.randint(3000, 8000))模拟人工操作节奏。5.2 拿到的 value 是加密字符串现象JSON 里value是一长串字母数字不是数字。原因百度指数对部分接口做了加密需要额外的解密步骤。解决优先拦截页面渲染后的数据而不是原始接口。可以在page.on(response)里过滤 URL 包含api且返回内容里value是数字的响应。如果所有响应都加密那就需要逆向解密逻辑这超出本文范围建议改用其他数据源或手动导出。5.3 日期对不上或缺少某几天现象DataFrame 里日期跳跃或者某几天是 NaN。原因指数数据本身在周末或节假日可能不更新或者接口返回的分页没取全。解决用pd.date_range生成完整日期序列然后reindex缺失的用前值填充。如果缺失太多检查是不是只取了第一页需要翻页逻辑。5.4 中文关键词 URL 编码问题现象关键词带中文时页面打开空白或报错。原因URL 里中文需要 percent-encoding。解决用urllib.parse.quote处理。from urllib.parse import quote keyword 数据分析 encoded quote(keyword) url fhttps://index.baidu.com/v2/main/index.html#/trend/{encoded}?words{encoded}5.5 多关键词时只返回了第一个词的数据现象同时传多个词但拦截到的 JSON 只包含一个词。原因页面可能分多次请求每个词一个请求。解决在on_response里不要提前 return把所有符合条件的响应都收集起来最后按关键词分组。或者干脆一个词一个词跑稳但慢。6. 进阶技巧用对比窗口和相关性矩阵挖出隐藏信号前面跑通了单次抓取和基础可视化但真正让百度指数分析产生价值的是把多个词放在同一时间窗口里做交叉验证。我常用的一个技巧是“滑动对比窗口”不只看全量趋势而是把时间轴切成 7 天一段计算每个词在每段里的环比变化率然后看哪些词的涨跌同步。def rolling_correlation(merged_df, window7): 计算多关键词在滑动窗口内的相关性 cols [c for c in merged_df.columns if c ! date] result [] for i in range(window, len(merged_df)): chunk merged_df.iloc[i-window:i][cols] corr chunk.corr().iloc[0, 1] # 取前两个词的相关系数 result.append({ date: merged_df.iloc[i][date], corr: corr }) return pd.DataFrame(result)这段代码输出的是两个词在每 7 天窗口内的皮尔逊相关系数。如果相关系数长期在 0.7 以上说明它们的热度联动性强如果某段时间突然跌到 0 以下可能发生了事件导致走势分化。这个信号比看静态对比图更敏感。另一个实用技巧是“峰值对齐”。把每个词的峰值日期找出来算它们之间的天数差。def peak_lag(merged_df, keywords): peaks {} for kw in keywords: idx merged_df[kw].idxmax() peaks[kw] merged_df.loc[idx, date] base min(peaks.values()) for kw, d in peaks.items(): print(f{kw} 峰值日期{d.date()}滞后基准 {(d - base).days} 天)如果 A 词峰值比 B 词早 3 天可能意味着 A 是先行指标B 是跟随指标。做内容排期时可以按这个滞后天数提前布局。最后说一个我踩过的坑不要用百度指数的绝对值去推算真实搜索量。指数是经过归一化和对数处理的相对值不同词的指数不可直接比大小只能比趋势。我曾经拿两个词的指数直接算比例结论完全跑偏。后来养成习惯所有分析都基于归一化后的相对变化结论反而更稳。希望帮到你。本文还有配套的精品资源点击获取
延伸阅读

更多相关文章

2026/10/22 3:12:31

5G NOMA功率分配仿真:SIC解码顺序与MATLAB实现

简介:面向5G通信与NOMA技术研究者,这份资源围绕非正交多址接入中的功率分配问题,提供从理论模型到仿真实现的完整参考,内容涵盖NOMA基本原理、基于用户SINR差异的功率约束策略、恒定与动态功率分配方法对比,并涉及干扰…

2026/10/22 3:12:31

分布鲁棒学习入门:从最坏情况思维到对偶优化

1. 为什么我要啃这本《Distributionally Robust Learning》第一次翻到《Distributionally Robust Learning》这本书的时候,我的反应和大多数人一样:标题里的每个单词都认识,连在一起就不知道在说什么了。Distributionally——分布层面的&…

2026/10/22 3:12:31

基于XGBoost的O2O优惠券预测:样本切分与特征工程实战指南

简介:这套项目面向高校毕业设计、课程设计与期末大作业场景,是一个基于XGBoost的O2O优惠券使用预测分析系统。项目围绕优惠券领取、核销与用户消费行为数据完成特征工程、模型训练与结果分析,并将算法能力封装为可操作的完整界面,…

2026/10/22 4:22:37

Redis作为AI短期记忆中枢的三大协同模式与数据建模实践

1. 为什么 Redis 突然成了 AI 系统的“记忆中枢”?最近在几个技术交流群里,频繁看到有人发截图:某大模型服务的响应延迟从 800ms 骤降到 120ms,监控图上 Redis 的 QPS 曲线同步冲高;另一份内部架构文档里,“…

2026/10/22 4:22:37

河北专升本汇编第四章:伪指令与程序设计核心考点突破

1. 为什么第四章是专升本汇编的分水岭1.1 从“能看懂”到“能写出来”的跨越河北专升本计算机专业的微机原理与接口技术这门课,很多人的复习轨迹是这样的:前三章学CPU结构、寄存器、存储器寻址,跟着视频课划划重点,做做选择题&…

2026/10/22 4:22:37

MediaPipe手部关键点实时跟踪:从零上手到手势识别实战

1. 从零上手MediaPipe手部关键点实时跟踪第一次接触MediaPipe是在一个体感交互的Demo项目里,当时需要在不依赖深度相机的前提下,仅用普通RGB摄像头完成手部21个关键点的实时定位。试过OpenPose的手部模型,帧率掉到个位数;也试过自…

2026/10/22 4:22:37

可预见误用的工程化:基于仿真的SOTIF误用场景构建与风险闭环

我在一次内部项目评审会上,身边一位产品负责人问了我一个问题:车辆已经发出接管的明确警告,前方也是施工路段的锥桶,驾驶员却低头刷了十分钟手机,最后车辆冲进锥桶堆,这个锅到底算谁的?当时会议…

2026/10/22 4:22:37

uniapp+Java选课系统实战:含MySQL事务、RBAC权限与真机调试

简介:本资源是一套面向高校计算机专业本科生的毕业设计/课程设计级移动端选课系统完整实现,聚焦教育信息化场景,解决传统选课流程中学生选退课不便、教师课程管理低效、教务数据分散等实际问题。资源包共978个文件,32.87MB&#x…

2026/10/22 4:17:36

从零手写AI艺术生成器:扩散模型DDPM原理与实现

朋友问我用什么AI工具画画,我一开始支支吾吾答不上来。不是不会用,而是我就会按几个按钮,底下的原理一问三不知。后来我较上劲了:直接用 Python 和深度学习,从零写一个 AI 艺术生成器——不调现成的图像生成接口&#…

2026/10/21 4:53:08

金融AI落地指南:从调研报告到技术选型与工程实践

简介:这份PDF报告聚焦2025年金融服务业中国AI现状与趋势,面向金融科技从业者、AI战略规划人员及关注行业数字化转型的研究者,帮助读者把握生成式AI在银行、支付、交易等场景中的落地路径与投资方向。资源包内含1个PDF文件,大小约1…

2026/10/22 0:01:49

电商智能运营体系从0到1:架构设计、落地步骤与避坑指南

前两年我们团队接了一个电商平台的运营中台项目,目标很直白:把过去靠运营拍脑袋做的选品、定价、发券、推活动这些事,逐步用数据算法和自动化流程代替。项目名字内部就叫“电商智能运营体系”。最近有不少朋友问我当时是怎么设计的、踩过哪些…

2026/10/22 0:01:49

若依框架AI代码生成不稳定?用Agent Skill三层结构+五步法搞定

最近一段时间,我一直想把后台管理系统里那些机械重复的增删改查代码交给AI去写。框架用的是若依,按理说这类业务代码模式非常固定,应该是AI最擅长的事情。可真试下来却不是那么回事——你让AI生成一个用户管理模块,它给出的Contro…

还想了解更多?直接咨询顾问

免费诊断 + 免费方案 + 透明报价。

全国咨询热线400-8866-253
免费获取方案
☎咨询二维码 ☎ ↑