浅析 Python 中数据离散化的实现方式
·
一、什么是数据离散化?
在数据分析和机器学习的预处理阶段,数据离散化是一个非常核心且常用的操作。
简单来说,数据离散化就是将连续的数值型数据,按照一定的规则划分成若干个离散的区间 / 类别。
- 连续数据:身高(175.5cm)、年龄(28 岁)、薪资(15000 元)
- 离散数据:青年、中年、高薪、低薪、[18-30]、[31-50]
为什么要做离散化?
- 简化模型:减少连续值的计算量,降低模型复杂度
- 提升效果:有效处理异常值,避免极端数据干扰模型
- 适配算法:决策树、朴素贝叶斯等算法更擅长处理离散特征
- 业务解读:离散后的特征更符合业务逻辑(如用户分层、价格分段)
二、Python 实现数据离散化的常用方式
本文基于Pandas库实现,这是 Python 数据分析最主流的工具,内置了cut()和qcut()两个专门用于离散化的函数,同时也支持自定义分箱逻辑。
环境准备
python
运行
import pandas as pd
import numpy as np
我们先生成一组测试数据(模拟用户年龄):
python
运行
# 生成100个18-70岁的随机年龄
np.random.seed(666) # 固定随机种子,结果可复现
ages = np.random.randint(18, 70, size=100)
df = pd.DataFrame({'age': ages})
三、方式 1:等宽分箱(pd.cut)
等宽分箱:按照固定的数值区间宽度划分数据,每个区间的长度相同。
核心函数:pd.cut()
用法 1:指定分箱个数
python
运行
# 将年龄分成4个等宽区间
df['age_cut'] = pd.cut(df['age'], bins=4)
print(df['age_cut'].value_counts().sort_index())
用法 2:自定义分箱边界(最常用)
python
运行
# 自定义区间:18-30,30-40,40-50,50-70
bins = [18, 30, 40, 50, 70]
df['age_cut_custom'] = pd.cut(df['age'], bins=bins)
# 给区间打标签(更直观)
labels = ['青年', '中青年', '中年', '中老年']
df['age_cut_label'] = pd.cut(df['age'], bins=bins, labels=labels)
等宽分箱特点
- 区间宽度固定
- 容易受异常值影响
- 适合分布均匀的数据
四、方式 2:等频分箱(pd.qcut)
等频分箱:按照数据数量划分,保证每个区间内的数据样本数量基本一致。
核心函数:pd.qcut()
python
运行
# 等频分成4组,每组数据量接近
df['age_qcut'] = pd.qcut(df['age'], q=4, labels=['Q1', 'Q2', 'Q3', 'Q4'])
print(df['age_qcut'].value_counts())
等频分箱特点
- 每个分组样本数相近
- 不受极端值影响
- 适合数据分布不均匀的场景
- 机器学习中最常用的离散化方式
五、方式 3:自定义函数离散化(灵活业务规则)
当业务有明确规则时(如:18 岁以下未成年,18-35 青年等),可以用apply+ 自定义函数实现。
python
运行
def age_discrete(age):
if age < 30:
return '青年'
elif age < 45:
return '中年'
elif age < 60:
return '壮年'
else:
return '老年'
# 应用函数
df['age_apply'] = df['age'].apply(age_discrete)
适用场景
- 业务规则明确
- 区间不固定、非对称
- 需要高度定制化的离散逻辑
六、方式 4:基于阈值 / 独热编码(One-Hot)离散化
在特征工程中,我们常将离散化后的特征转为独热编码,方便模型训练。
python
运行
# 先分箱
bins = [18, 30, 45, 60, 70]
df['age_bin'] = pd.cut(df['age'], bins=bins)
# 转为独热编码
age_dummies = pd.get_dummies(df['age_bin'], prefix='age')
df_new = pd.concat([df, age_dummies], axis=1)
这是建模前最标准的离散化 + 编码流程。
七、四种方式对比总结
表格
| 方式 | 函数 / 方法 | 特点 | 适用场景 |
|---|---|---|---|
| 等宽分箱 | pd.cut (固定 bins) | 区间宽度相同,简单直观 | 数据分布均匀、无明显异常值 |
| 等频分箱 | pd.qcut (q = 份数) | 每组样本数相近,抗干扰 | 数据倾斜、机器学习预处理 |
| 自定义函数 | apply+def | 高度灵活,贴合业务规则 | 业务定义明确的分段 |
| 独热编码离散 | get_dummies | 离散→编码,直接用于模型训练 | 建模前特征工程 |
八、完整可运行代码
python
运行
import pandas as pd
import numpy as np
# 1. 生成测试数据
np.random.seed(666)
ages = np.random.randint(18, 70, size=100)
df = pd.DataFrame({'age': ages})
# 2. 等宽分箱
bins = [18, 30, 40, 50, 70]
df['age_cut'] = pd.cut(df['age'], bins=bins, labels=['青年', '中青年', '中年', '中老年'])
# 3. 等频分箱
df['age_qcut'] = pd.qcut(df['age'], q=4, labels=['Q1', 'Q2', 'Q3', 'Q4'])
# 4. 自定义函数离散
def age_func(age):
if age < 30:
return '青年'
elif age < 45:
return '中年'
else:
return '老年'
df['age_apply'] = df['age'].apply(age_func)
# 5. 独热编码
df_dummies = pd.get_dummies(df['age_cut'], prefix='age')
# 展示结果
print("离散化结果预览:")
print(df.head(10))
九、总结
- 数据离散化是数据预处理的关键步骤,能简化数据、提升模型效果、增强业务可解释性。
- Python 中首选 Pandas 实现:
cut等宽、qcut等频最常用。 - 业务优先用自定义函数,建模优先用
qcut+独热编码。 - 没有绝对最优的离散方式,根据数据分布和业务需求选择。
本文适合人群
- 数据分析初学者
- 机器学习入门者
- 正在做特征工程的开发人员
更多推荐




所有评论(0)