如何让Seaborn FacetGrid显示百分比而非计数?
KMeans聚类后将FacetGrid直方图纵轴改为聚类内百分比
问题描述
我正在使用KMeans进行聚类任务,现有对应格式的数据集。我通过以下代码为每个特征绘制Seaborn FacetGrid直方图,按'Clusters'列分面:
for c in data: grid= sns.FacetGrid(data, col='Clusters') grid.map(plt.hist,c) grid.set_xticklabels(rotation=90)
当前输出图表显示各聚类中特征值的计数,但因不同聚类样本量有差异,计数对比参考价值有限。例如聚类1的客户年龄计数远高于聚类0,仅因聚类1样本更多。我需要将纵轴改为对应聚类内的百分比,实现每个特征在不同聚类中的占比对比,请问是否可行?
解决方案
当然可行,只需自定义绘图函数,在每个聚类子图内计算直方图的百分比即可,具体实现如下:
1. 自定义百分比直方图绘制函数
这个函数会自动计算当前聚类内各区间样本的占比,并绘制百分比直方图:
import matplotlib.pyplot as plt import seaborn as sns import numpy as np def plot_hist_percent(x, **kwargs): ax = plt.gca() # 计算直方图的计数和区间边界 counts, bins = np.histogram(x, bins='auto') # 计算每个区间的占比(转成百分比) percent = counts / counts.sum() * 100 # 绘制百分比直方图 ax.hist(bins[:-1], bins, weights=percent) # 设置纵轴标签为百分比 ax.set_ylabel('百分比 (%)')
2. 修改原循环代码
替换原有的plt.hist为自定义函数,同时跳过Clusters列本身:
for c in data.columns: if c == 'Clusters': continue grid = sns.FacetGrid(data, col='Clusters') grid.map(plot_hist_percent, c) grid.set_xticklabels(rotation=90) # 为子图添加特征名称标题,更清晰 grid.set_titles(col_template=f"聚类 {{col_name}} - {c}")
修改后,每个聚类子图的纵轴会显示该特征区间内样本占当前聚类总样本的百分比,彻底消除样本量差异带来的干扰,方便直接对比不同聚类间的特征分布占比。
内容的提问来源于stack exchange,提问作者Vinicio Araujo
相关产品推荐
相关产品推荐

