ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

Python得物商品数据可视化分析与协同过滤推荐系统实战

Python得物商品数据可视化分析与协同过滤推荐系统实战 每年到这个时间点总能看到一批人被毕业设计折腾得够呛。如果你手上摊着Python基于得物商品销售数据的可视化分析与推荐系统这个题目那恭喜它其实是一个被包装得很好的课题爬虫拿数据、Django做后端、协同过滤跑推荐、ECharts出可视化再塞一个基于大模型的agent做智能问答一条线能把电商数据链路从头摸到尾。这篇文章适合正在做毕设选题、或者想练手电商数据全流程的人我会按自己实际做过的项目顺序把这个题目的完整拆解、落地步骤和踩坑记录讲清楚。1. 项目全貌与选型思路这个课题到底值不值得做1.1 从标题拆解出完整的业务链路先别看这个标题长把它拆开其实就五个模块得物类潮流电商平台的商品数据、数据分析、可视化、协同过滤推荐、大模型agent。把它们串起来对应的是一条非常完整的业务数据链路——数据采集与清洗、指标体系建设、统计分析、推荐算法、智能交互。我做的时候第一反应是要不要把每个模块都做得很重后来发现完全没必要。毕业设计的核心不是单项技术多深而是能不能讲清楚一条完整的故事线。整条链路的起点是商品数据集包含品牌、价格、销量、尺码、上架时间、收藏数这些字段中间经过数据清洗和建模一方面输出给可视化大屏做全局分析另一方面输出给协同过滤算法构建用户和商品之间的行为关系最后再由大模型agent把查数据这件事变成自然语言对话比如问一句500到1000元价格带卖得最好的篮球鞋是哪几款它能听懂、能查出结果、还能给出解释。这套设计最讨喜的地方在于每个模块都有独立的工作量但又不是各干各的。推荐系统的结果可以反哺到可视化里可视化的指标口径又可以作为agent回答用户问题时的知识约束。你答辩的时候只要能把数据从哪来、经过了什么处理、在哪个模块被用掉这条线讲清楚基本就能接住老师的问题。1.2 Python Django为什么说这是毕业设计的稳妥牌技术选型上Python Django是一个几乎不会出错的组合。Python本身覆盖了数据采集、清洗、算法建模的全部需求pandas、numpy、scikit-learn这些库都是现成的不用在多个语言之间切换。Django的优势则是开箱即用四个字自带ORM、Admin后台、用户认证、模板渲染做一个需要前后端交互的完整系统比Flask省非常多事。我建议的版本组合是Python 3.10 Django 4.2 DRFDjango REST Framework。Django 4.2是目前稳定性最好的长期支持版本配合Python 3.10不会有兼容问题。如果你要写前后端分离的接口DRF几乎是标配序列化、分页、权限校验都内置好了比自己手写JsonResponse舒服太多。至于推荐算法为什么选协同过滤而不是深度学习理由也很实际第一毕设阶段的数据量通常就几千到几万条深度学习模型在这个规模下不会比协同过滤好第二协同过滤的可解释性很强因为你买过AJ所以给你推荐李宁匡威这句话答辩老师一听就懂第三实现成本低不需要GPU不需要训练十几个小时一个余弦相似度矩阵就能跑出效果。记住一个原则选题宁可用小但完整的组合也不要硬上大而残缺的模型。1.3 大模型agent的定位别把AI做成摆设这两年大模型特别火很多题目都喜欢往标题里加大模型三个字但加了不等于会用。我见过不少同学所谓大模型应用就是接一个对话接口用户问什么答什么跟系统本身的数据毫无关系——这种就是典型的摆设式AI答辩老师一问就露馅。真正有价值的做法是让大模型作为数据分析入口。用户输入一句自然语言比如最近30天销量下滑最明显的品牌是哪个agent先把这句话理解成一套结构化请求时间范围、统计维度、排序方式然后调用后端已经写好的查询工具拿到真实数据后再把数据组织成一段带结论的文字返回给用户。这个过程里大模型不是在凭空聊天而是在调用工具并解释结果这就是最实用的agent雏形。我实现的时候没有用任何重型的agent框架就是用大模型的function calling能力给模型声明几个工具函数比如get_sales_trend(brand, price_min, price_max, days)模型看到用户问题后会自己决定调用哪个函数、传什么参数我再在后端真正执行这个函数把结果喂回给模型生成最终回答。这套逻辑简单可靠又能在答辩时讲清楚意图识别-工具调用-结果生成的完整链路。2. 数据层怎么打基础采集、清洗、建模2.1 先想清楚要哪些字段再谈抓数据很多人一上来就写爬虫爬到什么算什么这是最大的坑。我在做之前先把数据字典列出来了最终确定的核心字段大概有这些商品ID、商品标题、品牌、一级分类篮球鞋/跑步鞋/板鞋等、价格、折扣前价格、销量、收藏数、上架时间、尺码区间、流行色、商品链接。这些字段不是随便定的每条都对应后面某个模块的需求。品牌、价格、销量是可视化大屏的统计分析基础销量和收藏数可以合成商品热度指标用于给协同过滤提供隐式反馈上架时间用于看趋势分类和尺码则是筛选和分群的前提。宁可前期把字段设计宽一点也不要后面反复改数据库表。采集方式上我用的方案是requests发请求拿页面HTML和接口JSON再用BeautifulSoup解析。这里提醒一句不要高频并发地去请求控制一下频率比如每请求一次随机sleep几秒再带上正常的User-Agent和Cookie避免被反爬策略针对。代码层面结构很简单核心就是请求-解析-提取-入库的循环但写的时候要加异常处理网络超时、页面结构变化、字段缺失都是常态。2.2 数据清洗的三个关键动作采集下来的数据一定脏别指望直接用。我整理下来必须做的清洗动作有三个。第一个是去重。商品ID是唯一键同一商品可能被重复爬到用pandas的drop_duplicates按商品ID去重即可。第二个是字段类型与格式统一。价格字段经常是字符串里面还可能带¥起券后这些杂字符销量可能是5000这种模糊表达品牌名大小写不一致。这些都要用正则和类型转换统一处理比如价格全部转成float销量把去掉后转成int。第三个是异常值剔除。价格低于1元或者高于99999元的数据基本是测试商品或错误数据直接过滤掉销量为负、上架时间为空的数据也一样处理。清洗之后的验证动作也很重要我会打印describe()看一眼每列的最大最小值、均值、缺失值数量确保没有离谱数据混进来。整个清洗逻辑建议封装成独立的脚本因为后面你很可能要补数据重新跑一遍清洗就完事了不用手动处理。2.3 商品、用户、行为三张核心表怎么建Django后端建模的时候我用的是三张核心表加两张辅助表的方案。商品表Shoe保存商品静态属性对应上面说的商品ID、标题、品牌、分类、价格、销量、上架时间这些字段。用户表User直接用Django内置的User扩展或者自己建一个UserProfile存用户的偏好信息。行为表Behavior是推荐系统的核心输入记录哪个用户对哪个商品产生了什么行为行为类型包括浏览、收藏、加入购物车、购买每种行为对应一个行为权重。外键关系上Behavior表用ForeignKey关联User和Shoe。这里有一个关键设计行为表必须加行为时间字段因为后面做协同过滤的离线评估时要把用户的行为按时间切分成训练集和测试集没有时间字段这个评估就做不了。商品表的品牌和分类字段建议加db_index索引因为可视化和推荐里会频繁按品牌、分类做筛选聚合没有索引的话数据量一上来查询会明显变慢。字段类型也有一些讲究价格用DecimalField不要用FloatField避免浮点误差销量用PositiveIntegerField上架时间用DateField商品标题和品牌用CharField并指定max_length。这样建表规范后面用ORM做聚合统计时也会顺手很多。2.4 业务指标口径必须先定下来可视化大屏和agent回答问题时离不开一套统一的指标口径。这个口径如果不提前定清楚就会出现前端图表的销量算法和后端接口的销量算法不一致的尴尬情况。我定下来的核心指标口径大概是这样的销售额等于销量乘以成交价这里用价格字段不额外处理活动折扣保持口径简单客单价等于总销售额除以订单用户数复购率等于购买次数大于1的用户占比动销率等于有销量商品数占全部商品数的比例。价格带划分按业务习惯来300元以下、300-500元、500-1000元、1000-2000元、2000元以上五个档位。推荐召回时要用的商品热度分我也定了个简单公式热度分 销量 * 0.6 收藏数 * 0.4直接归一化后用于冷启动场景的热门榜排序。这套口径一旦定下来后续所有模块都按它执行不要今天改明天又改否则你会发现自己被各种口径不一致的问题反复折腾。3. 协同过滤推荐系统从原理到Django接口3.1 UserCF还是ItemCF选型比写代码更重要协同过滤算法分两大类基于用户的协同过滤UserCF和基于物品的协同过滤ItemCF。很多教程会告诉你两者都要学但在实际项目里你必须根据业务场景做选型。基于物品的协同过滤更适用于鞋类电商这种垂直商品场景。核心逻辑是如果你喜欢A商品那么和你喜欢A的其他用户喜欢的B商品也可能被你喜欢换成ItemCF就是你买了AJ1我们找到和AJ1最相似的商品比如类似风格的Dunk或者同品牌的其他配色推荐给你。ItemCF的优点是推荐结果和用户历史行为直接相关、可解释性强而且商品之间的关系相对稳定不用频繁更新。UserCF则更适合内容社区、新闻资讯这类有强时效性的场景因为用户兴趣变化快、内容生命周期短。选型建议总结成一句话这个题目里你主要做的是商品推荐而不是内容推荐所以ItemCF是更稳妥的主算法。当然答辩时可以把两种算法都实现出来做对比实验然后给出哪个指标更好、为什么更好的结论这会是一个很好的加分项。3.2 评分矩阵与相似度计算的实现细节协同过滤的第一步是构建用户-商品评分矩阵行是用户列是商品值是评分或行为权重。我没有用显式评分鞋子平台本来就没有给商品打分的强场景而是通过行为权重合成隐式评分浏览记0.5分、收藏记1分、加入购物车记2分、购买记3分。如果一个用户对同一商品有多个行为分数累加。这样得到的是一个稀疏但是有商业含义的评分矩阵。相似度计算我用的是余弦相似度。商品A和商品B的向量分别是所有用户对它们的评分向量两个向量夹角的余弦值越接近1说明这两个商品被同一批用户喜欢的程度越一致。代码实现上我直接用了pandas构建DataFrame、用scikit-learn的cosine_similarity计算这比自己写循环快得多且不容易出错。矩阵规模大的时候要注意内存问题用户数和商品数过万之后稠密矩阵会非常占内存这时候要用scipy.sparse的稀疏矩阵格式。我当时数据量在5000个用户、3000个商品左右df.pivot_table构建出来的矩阵里95%以上都是空值换成CSR稀疏矩阵之后内存占用直接降到原来的几十分之一。3.3 把协同过滤结果封装成推荐API算法跑通之后要把结果变成Django接口给前端调用。我的做法是推荐接口设计为GET /api/recommend/?user_idxxxtop_n10。后端流程是先从Behavior表查出当前用户的行为记录找出他买过或收藏过的商品集合再在之前算好的商品相似度矩阵里找出这些种子商品各自最相似的TopN商品然后按相似度加权汇总过滤掉用户已经购买过的商品最后按加权得分排序取前top_n返回。相似度矩阵怎么存这是一个容易踩坑的点。最简单的方式是训练完成后把商品A-商品B-相似度三元组存到数据库的一张item_sim表里推荐时直接查表。缺点是数据量大了查询慢。另一种方式是每次启动服务时把矩阵load进Redis查询走内存速度快很多。我做毕设时用的方案是矩阵规模小就存数据库表规模超过一万条记录就放Redis两者代码相差不大可以都实现再对比。接口返回的JSON结构我会定义成统一格式包含商品ID、标题、品牌、价格、销量、推荐理由字段。这个推荐理由字段就是可解释性的体现——因为你收藏了Dunk Low所以推荐同风格的运动板鞋前端把这句话直接展示出来整个系统的完成度一下就上去了。3.4 冷启动和离线评估答辩必问的两个问题如果答辩老师只问三个问题冷启动和效果评估一定占两个。冷启动有三类新用户冷启动、新商品冷启动、系统冷启动。新用户没有行为数据协同过滤完全无法工作。我的处理方案是分两步先用热门榜兜底把热度分Top20的商品推荐给新用户再让用户在登录时选一下偏好的品牌和价格带基于这些标签做粗筛。新商品冷启动同理没有行为数据就把同品牌、同分类、最近上架的商品作为替代推荐同时给予一定的曝光加权。系统冷启动就是整个库里没有行为数据的情况这时候只能做基于商品属性的相似推荐也就是用品牌、分类、价格带之间的距离来计算内容相似度。离线评估我用的是时间切分法把每个用户的行为按时间排序取最后20%作为测试集前80%作为训练集。用训练集训练推荐模型在测试集上看推荐结果中有多少商品是用户真实交互过的计算命中率Hit Rate和召回率。我当时的实测结果ItemCF的Top10命中率大概在22%到30%之间这个数字不算惊艳但对于答辩来说已经足够说明算法有效了。4. 可视化分析大屏图表怎么选、数据怎么给4.1 一屏看清谁在卖、卖什么、卖多少钱可视化大屏是整套系统里最直观、最能撑场面的部分但很多人的大屏只是堆图表没有分析逻辑。我在设计大屏时问了自己三个问题谁在卖品牌格局、卖什么品类结构、卖多少钱价格分布。围绕这三个问题大屏的布局我这样安排顶部一排指标卡放总商品数、总销量、总销售额、平均客单价四个核心指标中间主体区域放销量趋势折线图近12个月和品牌销量Top10柱状图左侧放价格带分布饼图和尺码分布环形图右侧放商品热度散点图销量与收藏量的关系以及热门商品词云。这样整个大屏从上到下、从左到右覆盖了从宏观指标到微观商品的全部分析视角。图表选型上也有讲究时间趋势用折线图排名对比用柱状图结构占比用饼图两个数值维度的关系用散点图文本关键词用词云。不要为了炫技用一堆3D图表答辩时老师更看重的是你选的图表是否准确表达了业务含义。4.2 Django后端聚合接口用ORM减少查询量大屏上的每一个图表背后都应该有一个数据接口不要在前端拿全量数据自己算。我在Django里设计了一组统计接口/api/stats/overview返回顶部指标卡数据/api/stats/trend返回按月份聚合的销量趋势/api/stats/brand_rank返回品牌销量Top10/api/stats/price_dist返回价格带分布/api/stats/category_dist返回品类和尺码分布。关键实现技巧是善用Django ORM的annotate聚合。以品牌销量Top10为例一行查询就能搞定Shoe.objects.values(brand).annotate(total_salesSum(sales)).order_by(-total_sales)[:10]。这条语句在数据库层面完成分组和求和不会把全表数据拉到Python内存里性能好很多。还有一个细节统计结果不是每次请求都实时算的。我当时给统计接口加了一层Redis缓存缓存键可以设计成统计类型加时间范围比如stats:brand_rank:2025缓存过期时间设为一小时。这样大屏刷新时不会反复压数据库演示的时候数据加载也明显更快。4.3 pyecharts与前端渲染的集成细节图表的渲染方案我推荐pyecharts它基于ECharts封装Python语法生成图表配置对熟悉pandas的同学特别友好。用法简单到像是写配置字典创建Bar对象、加入x轴和y轴数据、set_global_opts设置标题和坐标轴一个柱状图就出来了。把pyecharts嵌入Django主流有两种方式。方式一是在Django视图里直接调用图表对象的render_embed()生成本地HTML片段塞进模板方式二是图表数据以JSON格式传给前端由前端的ECharts实例负责渲染。毕设演示场景下我推荐方式一因为省事且稳定但如果你打算做前后端分离就选方式二。集成时有一个容易被忽略的坑pyecharts生成的HTML会引用ECharts的JS依赖本地离线演示时可能会加载失败。解决办法是把依赖JS文件下载到static目录或者用render_embed()配合本地打包好的echarts.min.js确保在没有外网的环境下图表也能正常显示。5. 大模型agent给系统加一个会查数的AI助手5.1 功能设计自然语言查数和智能推荐解释大模型agent在系统里承担两个任务。第一个是自然语言查数用户用中文提问系统返回数据答案并生成分析文字。第二个是智能推荐解释也就是把协同过滤的结果翻译成人话比如推荐页签里显示因为你近期收藏了多款联名款球鞋系统为你重点推荐了同风格的商品。这两个功能落到实处都是同一套技术大模型负责理解和生成后端函数负责真正执行查询。我把这个模块做成一个独立的分析助手页面用户在输入框里提问后端把问题转成工具调用并执行最后把答案流式地返回展示。这个页面天然就是一个完整的前后端交互demo工作量不大但观感非常好。设计时我坚持了一点所有返回给用户的数据都必须来自真实数据库大模型不能自己编数字。为了避免模型胡编我会在提示词里反复强调只能基于工具返回的数据进行回答如果工具没有返回数据请直接告知用户暂时没有相关数据。这条约束约束好了agent的可信度才会高。5.2 提示词模板与工具调用agent的实现我分成了三部分系统提示词、工具定义、执行循环。系统提示词设定角色我写的大意是你是某鞋类电商平台的数据分析助手负责根据工具返回的数据回答用户问题。回答时先给出结论再简要解释数据依据。工具定义部分告诉模型有哪些函数可以调用。以get_brand_sales_rank为例工具描述里写明参数含义包括品牌、价格区间、时间范围、排序方式。模型看到用户问题300到800元之间销量前十的篮球鞋品牌后会自动把参数解析成price_min300、price_max800、category篮球鞋、top_n10并选择调用这个工具。执行循环是标准的function calling流程把用户问题连同工具定义发给大模型模型返回一个要调用工具的响应后端解析出工具名和参数执行对应的Django查询函数把查询结果以JSON字符串的形式追加到对话里再次发给模型模型基于真实数据生成最终文本回复。这个往返流程就是最简洁的agent机制核心代码量并不多逻辑也清晰。5.3 流式输出与接口安全大模型接口响应时间通常在一秒到几秒之间如果让用户干等体验会很差。我建议用流式输出优化调用大模型接口时开启stream参数把模型逐步生成的token通过SSE推给前端效果就是打字机式逐字输出。Django里可以用StreamingHttpResponse实现SSE前端用EventSource或者fetch的ReadableStream接收代码量不大但体验提升非常明显。接口安全方面有几个细节。大模型的API密钥绝不能写在settings.py里直接提交要放到环境变量或者本地配置文件中并加入.gitignore。接口要做访问控制最简单的是加token校验登录用户才能调用agent接口避免密钥被消耗。成本控制也要注意提示词不要太长回答的max_tokens限制在300左右温度调低到0.3以下这样回答更稳定也更省钱。6. 实操复盘我踩过的坑和排查清单6.1 评分矩阵构建时最容易翻车的三个点第一个坑是用户ID和商品ID没有转为统一的数字编码。文本ID进矩阵会让pandas的pivot_table建出一个巨大而且奇怪的索引后续做相似度计算会出错。解决办法是先分别做用户和商品的编码映射字典保证矩阵的行列都是连续的整数索引。第二个坑是空值处理。用户-商品评分矩阵极度稀疏直接对包含NaN的矩阵做余弦相似度计算会得到大量无意义结果。我的做法是先用fillna(0)把评分矩阵填零再调cosine_similarity。注意不要在填充前先做中心化否则零值全变成负值相似度含义就变了。第三个坑是只算有交集的向量。如果两个商品几乎没有共同用户它们的余弦相似度要么为0要么数值不稳应该设置一个最低共同用户数阈值比如共同用户数少于5的直接丢弃。这个阈值能过滤掉大量随机噪声推荐质量会明显提升。6.2 Django与可视化集成的两条路线可视化集成路线我两条都试过给你一个明确的选择建议。如果你的页面是Django模板渲染的传统多页应用直接选pyecharts的render_embed()视图里返回一个包含图表HTML的字符串模板用safe过滤器渲染半小时就能把所有图表挂上去。如果你打算做成前后端分离的单页应用那就让Django只提供JSON接口前端用原生ECharts或Vue/React来渲染。这条路线工作量更大但页面会更灵活后续接大模型agent的流式输出也更顺畅。我当时是混合方案大屏页面用Django模板加pyechartsagent页面用前后端分离加SSE。这样两种渲染方式都涉及到了PPT里还能多讲一个技术点算是性价比很高的组合。6.3 常见报错速查表我把做这个项目过程中碰到的高频问题和解决方案整理成了清单做的时候可以直接对着排查。pip安装Django时报版本冲突多数是Python版本过低。Django 4.2要求Python 3.8以上建议直接升到Python 3.10再装。运行数据库迁移时报Table already exists一般是之前迁移中断过解决办法是手动删除数据库中的django_migrations记录后重新migrate。页面表单提交时报CSRF verification failedDjango默认开启了CSRF校验模板表单里加csrf_token即可。跨域调用接口报CORS错误安装django-cors-headers并把前端域名加进白名单。pyecharts图表中文乱码通常是系统缺少中文字体或者IDE的默认编码不是UTF-8统一用UTF-8并在绘图配置里指定中文字体即可。agent接口调用报超时建议把大模型请求放到独立线程执行接口先返回任务ID前端再轮询或通过WebSocket接收结果避免HTTP请求长时间挂起。这个方案虽然多了一点代码量但稳定性明显优于直接同步等待。最后说点掏心窝的话。这套系统我前后改了三版第一版只做推荐答辩老师连问三个数据口径的问题我就答不上来第二版加了可视化大屏能看到的东西多了第三版把大模型agent接进去之后面试官的第一反应是这个工作量确实可以。但给你一个建议毕设源码可以借鉴但每个模块的中间结果、每个参数为什么这样定你一定要能自己推导出来。别等到答辩站在讲台上才发现自己连价格带为什么分五档都解释不清楚。希望你做完这套系统时不仅拿到了代码还真正把电商数据链路这回事弄明白了。
返回列表