如何基于两个向量的分箱值使用Numpy高效填充排序矩阵
解决方案
首先你之前初始化矩阵的代码需要修正,n个分箱边界对应n-1个有效分箱,因此矩阵的列数应为len(bins)-1而非len(bins)。
你可以通过分箱内元素序号+高级索引的方式高效完成赋值,不需要循环逐元素处理,适合大规模数组场景。
完整实现代码
纯Numpy版本(无额外依赖)
import numpy as np # 原有分箱逻辑 X = np.array([1,3,5,4,5,7,2,4,5]) V = np.array([0.5,0.7,0.29,4.4,13.3,0.9,2.2,2.7,2.5]) grid_max = X.max() grid_min = X.min() bin_width = int(3) bins = np.arange(grid_min, grid_max + bin_width, bin_width) binplace_X = np.digitize(X, bins) # 修正矩阵初始化的列数 Sort = np.full((X.shape[0], len(bins)-1), np.nan) # 生成每个元素在对应分箱内的行索引 sorter = np.argsort(binplace_X) sorted_bins = binplace_X[sorter] # 统计每个分箱的元素数量 _, bin_counts = np.unique(sorted_bins, return_counts=True) # 生成每个分箱内的递增序号 row_in_bin = np.concatenate([np.arange(c) for c in bin_counts]) # 将序号映射回原数组的顺序 original_row_idx = np.zeros_like(binplace_X) original_row_idx[sorter] = row_in_bin # 列索引:将digitize返回的1-based编号转为0-based col_idx = binplace_X - 1 # 批量赋值 Sort[original_row_idx, col_idx] = V
Pandas简化版本
如果你可以使用pandas,分箱内序号的生成逻辑可以大幅简化:
import pandas as pd # 前面的分箱计算逻辑保持不变 # 直接生成分箱内的递增序号 original_row_idx = pd.Series(binplace_X).groupby(binplace_X).cumcount().values col_idx = binplace_X - 1 Sort[original_row_idx, col_idx] = V
输出验证
运行后打印Sort即可得到你期望的结果:
array([[ 0.5 , 0.29, 0.9 ], [ 0.7 , 4.4 , nan], [ 2.2 , 13.3 , nan], [ nan, 2.7 , nan], [ nan, 2.5 , nan], [ nan, nan, nan], [ nan, nan, nan], [ nan, nan, nan], [ nan, nan, nan]])
内容的提问来源于stack exchange,提问作者ValientProcess
相关产品推荐
相关产品推荐

