900万条记录数据库中产品共购分析的Python高效实现咨询
高效实现产品关联购买频次分析
针对你900万条记录、5万种产品的场景,原代码的嵌套循环+列表推导完全无法处理这种规模的数据——仅两层循环就会产生2.5亿次迭代,每次还要全量扫描数据集,时间复杂度高到离谱。下面用pandas+稀疏矩阵的方案彻底解决效率问题:
核心思路
我们不需要遍历所有产品组合,而是利用用户-产品二元矩阵的转置乘法直接计算共现频次:
- 先构建“用户-是否购买某产品”的稀疏矩阵(仅存储购买过的记录,节省内存)
- 矩阵转置后与原矩阵相乘,得到的结果矩阵中,
[i,j]的值就是同时购买产品i和产品j的用户数
具体实现代码
import pandas as pd from scipy.sparse import csr_matrix from sklearn.preprocessing import LabelEncoder # 1. 加载并预处理数据 # 替换为你的数据加载方式(比如read_csv、read_sql等) df = pd.read_csv('your_dataset.csv') # 去重:同一个用户对同一个产品的多次购买只保留1条(我们只关心是否购买,不关心购买数量) user_product = df[['user_id', 'product_id']].drop_duplicates() # 2. 对用户和产品做整数编码(稀疏矩阵需要整数索引) user_encoder = LabelEncoder() product_encoder = LabelEncoder() user_product['user_idx'] = user_encoder.fit_transform(user_product['user_id']) user_product['product_idx'] = product_encoder.fit_transform(user_product['product_id']) # 3. 构建稀疏矩阵:行=用户索引,列=产品索引,值=1(表示该用户购买过该产品) sparse_matrix = csr_matrix( ([1] * len(user_product), (user_product['user_idx'], user_product['product_idx'])) ) # 4. 计算产品共现矩阵:转置矩阵点乘原矩阵,直接得到所有产品的共现频次 co_occurrence_matrix = sparse_matrix.T.dot(sparse_matrix) # 5. 转换为易读的DataFrame(索引和列名都是原始产品ID) co_occurrence_df = pd.DataFrame( co_occurrence_matrix.toarray(), index=product_encoder.classes_, columns=product_encoder.classes_ ) # 示例:查询productA和productB的共同购买用户数 # print(co_occurrence_df.loc['productA', 'productB'])
为什么这个方案高效?
- 内存优化:稀疏矩阵仅存储非零值(即用户确实购买过的产品记录),避免了存储5万列×数百万行的全量矩阵(这会直接耗尽内存)
- 计算效率:矩阵乘法用Scipy的底层优化实现(C语言),比Python循环快几个数量级,处理5万产品的共现计算仅需几秒到几分钟
- 避免冗余计算:一次性计算所有产品组合的共现频次,不需要遍历每一对产品
额外优化建议
- 如果只需要分析特定产品的关联,可以在构建稀疏矩阵后只提取对应产品的列,再计算共现,进一步节省计算资源
- 如果用户ID或产品ID是字符串类型,LabelEncoder编码是必须的;如果已经是整数,可以跳过编码步骤
内容的提问来源于stack exchange,提问作者Allanon
相关产品推荐
相关产品推荐

