在Julia中为对数-对数刻度直方图添加幂律分布拟合线
问题描述
我有一组节点度数数据,已通过以下代码绘制出对数-对数刻度的直方图:
histogram(log.(degree), bins=50, yaxis = (:log10)) title!("Degree distribution (log-log scale)")
希望在该直方图上添加一条幂律分布拟合线,以此展示数据符合幂律分布的特征。
解决方案
要实现这个需求,需先对度数数据做幂律参数估计,再基于直方图的刻度范围绘制拟合线,具体步骤如下:
1. 估计幂律分布参数
幂律分布的形式为 ( P(k) \propto k^{-\gamma} ),其中 ( k ) 为度数,( \gamma ) 是幂指数。可通过最大似然估计计算参数:
using Distributions # 过滤度数为0的节点(幂律分布在k=0处无定义) valid_degree = degree[degree .> 0] # 拟合幂律分布,得到最小拟合度数xmin和幂指数gamma xmin, gamma = fit_power_law(valid_degree)
2. 计算拟合线的坐标
基于直方图的bin范围,计算每个bin中点对应的幂律分布计数(适配对数刻度和直方图归一化规则):
# 先绘制直方图并获取其bin信息 h = histogram(log.(valid_degree), bins=50, yaxis=(:log10), label="度数直方图") bin_edges = h.plots[1].xedges bin_counts = h.plots[1].y # 计算每个bin的中点(原始度数的对数) bin_mid_log = (bin_edges[1:end-1] .+ bin_edges[2:end]) ./ 2 bin_mid = exp.(bin_mid_log) # 计算幂律拟合线的y值(匹配直方图的计数刻度) bin_width = bin_edges[2] - bin_edges[1] total_samples = length(valid_degree) power_law_y = total_samples * bin_width .* (gamma - 1) ./ xmin .* (bin_mid ./ xmin) .^ (-gamma)
3. 叠加拟合线到直方图
用plot!函数将拟合线添加到已绘制的直方图上:
plot!(bin_mid_log, power_law_y, label="幂律拟合 (γ=$(round(gamma, digits=2)))", linewidth=2, color=:red) title!("Degree distribution (log-log scale)") xlabel!("log(度数)") ylabel!("log(计数)") legend!()
注意事项
- 若未安装
Distributions包,先执行Pkg.add("Distributions")完成安装 - 必须过滤度数为0的样本,否则无法进行幂律拟合
- 拟合线的y值计算需结合bin宽度和总样本数,才能与直方图的计数刻度匹配
内容的提问来源于stack exchange,提问作者Chao
相关产品推荐
相关产品推荐

