displot()与plot()绘制PDF差异:为何displot()无法生成正态分布图?
问题:displot()与plot()绘制正态PDF结果不一致的原因
我用displot()和plot()两种方法可视化正态分布的概率密度函数(PDF),发现displot()生成的图形完全不符合预期,而plot()能完美输出标准的钟形正态曲线。明明两者应该得到一致的密度图,请问displot()的问题出在哪?
代码示例1(displot()实现)
from scipy.stats import norm import seaborn as sns import numpy as np data_x= np.arange(-4, 4, 0.001) norm_pdf = norm.pdf(data_x) sns.displot(data = norm_pdf, x = data_x, kind='kde')
对应图形:呈现出一条奇怪的扁平曲线,完全不是预期的钟形正态分布。
代码示例2(plot()实现)
from scipy.stats import norm import matplotlib.pyplot as plt import numpy as np data_x= np.arange(-4, 4, 0.001) plt.plot(data_x, norm.pdf(data_x)) plt.show()
对应图形:标准的钟形正态分布曲线,完全符合预期。
问题原因
seaborn的displot()(当指定kind='kde'时)的核心逻辑是基于输入的样本数据,通过核密度估计(KDE)来拟合分布,而不是直接绘制你传入的x-y坐标对。
你错误地把预先计算好的PDF值(norm_pdf)传给了data参数,同时把data_x传给x参数——这相当于让seaborn把norm_pdf当成一组样本数据(这些数据的取值范围在0到0.4之间),然后对这组数据做KDE估计,最终画出的是这组PDF值的分布,而不是你想要的正态分布PDF曲线。
反观plt.plot(),它是直接根据你传入的data_x(x轴)和norm.pdf(data_x)(y轴)坐标点连线,所以能准确绘制出预先计算好的PDF曲线。
修正方案
方案1:用kdeplot()直接绘制x-y曲线
如果你已经预先计算好了PDF值,改用seaborn的kdeplot()并指定x和y参数,就能实现和plot()一样的效果:
from scipy.stats import norm import seaborn as sns import numpy as np data_x = np.arange(-4, 4, 0.001) norm_pdf = norm.pdf(data_x) sns.kdeplot(x=data_x, y=norm_pdf, fill=False, linewidth=2)
方案2:让displot()基于样本数据估计KDE
这更符合seaborn的设计初衷:生成一组正态分布的样本数据,让displot()自动通过KDE拟合出分布曲线:
from scipy.stats import norm import seaborn as sns import numpy as np # 生成10000个标准正态分布的样本 sample_data = norm.rvs(size=10000) sns.displot(data=sample_data, kind='kde')
内容的提问来源于stack exchange,提问作者mustafa00
相关产品推荐
相关产品推荐

