基于Pandas列动态创建分箱:使观测数约为总计数的1%
Pandas数值列动态分箱实现方案
数据基础信息
Total rows 34149 Mean 4112195398.901 Min -1687500000 Median 44531800 Max 56956420100000
注:该列无零值
分箱规则
- 所有负值归为-1分箱
- 20000000以内采用1000000的分箱宽度
- 20000000以上动态调整分箱宽度,使每个分箱的观测数(NOBS)约为总计数的1%,即当观测数低于总计数1%时调整宽度满足要求
已实现的前两类分箱代码
df_ = df['Col1'].dropna() df_1 = pd.Series(np.where(df_ < 0, -1, pd.Series(df_/1000000).astype(int))) df_2 = pd.DataFrame(df_1, columns=['Bins']) df_bins = df_2.value_counts(sort=False).reset_index(name='NOBS') df_bins['Percentage'] = (df_bins['NOBS']/df_bins['NOBS'].sum())*100
现有分箱输出示例
Bins NOBS Percentage -1 195 0.943 0 2155 10.420 1 1594 7.707 2 1209 5.846 3 970 4.690 ...
第三类动态分箱实现方法
实现思路
- 从现有分箱结果中筛选出20000000以上的数据(对应
df_bins中Bins>20的行,因20000000/1000000=20) - 计算目标观测数:总数据量的1%,即
target_nobs = int(len(df_) * 0.01) - 迭代合并相邻分箱,直到每个分箱的观测数接近目标值
- 将处理后的动态分箱与前两类分箱合并,保持分箱为整数格式
具体代码实现
import pandas as pd import numpy as np # 提取2000万以上的分箱数据 above_20m = df_bins[df_bins['Bins'] > 20].copy().reset_index(drop=True) # 计算目标观测数:总条数的1% target_nobs = int(len(df_) * 0.01) # 动态合并分箱 merged_bins = [] current_bin_start = above_20m['Bins'].iloc[0] current_nobs = above_20m['NOBS'].iloc[0] for i in range(1, len(above_20m)): if current_nobs + above_20m['NOBS'].iloc[i] < target_nobs: # 合并到当前分箱 current_nobs += above_20m['NOBS'].iloc[i] else: # 保存当前分箱 merged_bins.append({ 'Bins': current_bin_start, 'NOBS': current_nobs, 'Percentage': (current_nobs / len(df_)) * 100 }) # 重置当前分箱参数 current_bin_start = above_20m['Bins'].iloc[i] current_nobs = above_20m['NOBS'].iloc[i] # 添加最后一个未完成合并的分箱 merged_bins.append({ 'Bins': current_bin_start, 'NOBS': current_nobs, 'Percentage': (current_nobs / len(df_)) * 100 }) # 转换为DataFrame merged_bins_df = pd.DataFrame(merged_bins) # 合并前两类分箱和动态分箱结果 final_bins = pd.concat([ df_bins[df_bins['Bins'] <= 20], merged_bins_df ]).reset_index(drop=True) # 重新计算百分比,避免浮点误差导致总和不为100% final_bins['Percentage'] = (final_bins['NOBS'] / final_bins['NOBS'].sum()) * 100
代码说明
- 分箱标识采用起始分箱的整数值,若需要范围形式(如"21-30"),只需修改
merged_bins中的'Bins'字段格式即可 - 合并逻辑优先保证分箱观测数接近目标值,若最后一个分箱观测数不足1%,直接保留为单独分箱
- 重新计算百分比可消除浮点运算带来的误差,确保总和始终为100%
内容的提问来源于stack exchange,提问作者Suhas_Pote
相关产品推荐
相关产品推荐

