如何用Python高效获取scipy.stats.binned_statistic_2d的分箱编号?
高效生成分箱编号列的方法
你不需要嵌套循环,stats.binned_statistic_2d返回的binnumbers已经包含了每个样本对应的二维箱号,直接用NumPy的向量化函数就能快速生成唯一的一维分箱编号:
实现步骤
- 利用返回的
binnumbers(形状为(N, 2),每一行对应纬度、经度的箱编号),通过numpy.ravel_multi_index将二维箱号转换为唯一的一维编号。这个函数会根据x、y方向的箱总数,把二维索引映射成连续的一维整数,完全向量化,速度极快。 - 将生成的一维编号直接赋值给DataFrame的新列。
完整代码示例
import numpy as np from scipy import stats # 假设你的df和bins已经定义好 df = df[['unique_id','Latitude','Longitude']] # 执行二维分箱 stats_result, yedges, xedges, binnumbers = stats.binned_statistic_2d( df['Latitude'].values, df['Longitude'].values, values=df['unique_id'].values, bins=bins, statistic='count' ) # 计算x、y方向的箱数量(edges的长度是箱数+1,所以要减1) num_y_bins = len(yedges) - 1 num_x_bins = len(xedges) - 1 # 将二维箱号转换为唯一的一维分箱编号 df['binnumber'] = np.ravel_multi_index( (binnumbers[:, 0] - 1, binnumbers[:, 1] - 1), # 箱号是1-based,转成0-based索引 (num_y_bins, num_x_bins) )
说明
binnumbers返回的箱号是1-based计数(从1开始),而ravel_multi_index需要0-based索引,所以要减1适配。- 这种方法完全基于NumPy的向量化操作,避免了Python层面的循环,处理大规模数据时效率远高于嵌套循环。
- 最终
df会新增binnumber列,每个值对应该行样本所属的唯一分箱编号。
内容的提问来源于stack exchange,提问作者jrange27
相关产品推荐
相关产品推荐

