MCMC: Convergence and Example


Lecture 15

March 20, 2024

Last Class(es)

Markov Chain Strategy

  • Generate an appropriate Markov chain so that its stationary distribution of the target distribution \(\pi\);
  • Run its dynamics long enough to converge to the stationary distribution;
  • Use the resulting ensemble of states as Monte Carlo samples from \(\pi\) .

Markov Chain Convergence

Given a Markov chain \(\{X_t\}_{t=1, \ldots, T}\) returned from this procedure, sampling from distribution \(\pi\):

  • \(\mathbb{P}(X_t = y) \to \pi(y)\) as \(t \to \infty\)
  • This means the chain can be considered a dependent sample approximately distributed from \(\pi\).
  • The first values (the transient portion) of the chain are highly dependent on the initial value.

The Metropolis-Hastings Algorithm

Given \(X_t = x_t\):

  1. Generate \(Y_t \sim q(y | x_t)\);
  2. Set \(X_{t+1} = Y_t\) with probability \(\rho(x_t, Y_t)\), where \[\rho(x, y) = \min \left\{\frac{\pi(y)}{\pi(x)}\frac{q(x | y)}{q(y | x)}, 1\right\},\] else set \(X_{t+1} = x_t\).

Proposals

  • “Goldilocks” proposal: acceptance rate 30-45%.
  • Proposal distribution \(q\) plays a big role in the effective sample size (ESS): \[N_\text{eff} = \frac{N}{1+2\sum_{t=1}^\infty \rho_t}\]

Sampling Efficiency Example

MCMC Sampling for Various Proposals

MCMC Convergence

Transient Chain Portion

What do we do with the transient portion of the chain?

  • Discard as burn-in;
  • Just run the chain longer.

How To Identify Convergence?

Short answer: There is no guarantee! Judgement based on an accumulation of evidence from various heuristics.

  • The good news — getting the precise “right” end of the transient chain doesn’t matter.
  • If a few transient iterations remain, the effect will be washed out with a large enough post-convergence chain.

Heuristics for Convergence

Compare distribution (histogram/kernel density plot) after half of the chain to full chain.

2000 Iterations

10000 Iterations
Figure 1

Gelman-Rubin Diagnostic

Gelman & Rubin (1992)

  • Run multiple chains from “overdispersed” starting points
  • Compare intra-chain and inter-chain variances
  • Summarized as \(\hat{R}\) statistic: closer to 1 implies better convergence.
  • Can also check distributions across multiple chains vs. the half-chain check.

On Multiple Chains

Unless a specific scheme is used, multiple chains are not a solution for issues of convergence, as each individual chain needs to converge and have burn-in discarded/watered-down.

This means multiple chains are more useful for diagnostics, but once they’ve all been run long enough, can mix samples freely.

Heuristics for Convergence

  • If you’re more interested in the mean estimate, can also look at the its stability by iteration or the Monte Carlo standard error.
  • Look at traceplots; do you see sudden “jumps”?
  • When in doubt, run the chain longer.

Increasing Efficiency

Adaptive Metropolis-Hastings

Adjust proposal density to hit target acceptance rate.

  • Need to be cautious about detailed balance.
  • Typical strategy is to adapt for a portion of the initial chain (part of the burn-in), then run longer with that proposal.

Hamiltonian Monte Carlo

  • Idea: Use proposals which steer towards “typical set” without collapsing towards the mode (based on Hamiltonian vector field);
  • Requires gradient information: can be obtained through autodifferentiation; challenging for external models;
  • Can be very efficient due to potential for anti-correlated samples, but very sensitive to parameterization.
  • Same principles for evaluating convergence apply.

MCMC Example: Modeling Storm Surge Extremes

Data

Code
# load SF tide gauge data
# read in data and get annual maxima
function load_data(fname)
    date_format = DateFormat("yyyy-mm-dd HH:MM:SS")
    # This uses the DataFramesMeta.jl package, which makes it easy to string together commands to load and process data
    df = @chain fname begin
        CSV.read(DataFrame; header=false)
        rename("Column1" => "year", "Column2" => "month", "Column3" => "day", "Column4" => "hour", "Column5" => "gauge")
        # need to reformat the decimal date in the data file
        @transform :datetime = DateTime.(:year, :month, :day, :hour)
        # replace -99999 with missing
        @transform :gauge = ifelse.(abs.(:gauge) .>= 9999, missing, :gauge)
        select(:datetime, :gauge)
    end
    return df
end

dat = load_data("data/surge/h551.csv")

# detrend the data to remove the effects of sea-level rise and seasonal dynamics
ma_length = 366
ma_offset = Int(floor(ma_length/2))
moving_average(series,n) = [mean(@view series[i-n:i+n]) for i in n+1:length(series)-n]
dat_ma = DataFrame(datetime=dat.datetime[ma_offset+1:end-ma_offset], residual=dat.gauge[ma_offset+1:end-ma_offset] .- moving_average(dat.gauge, ma_offset))

# group data by year and compute the annual maxima
dat_ma = dropmissing(dat_ma) # drop missing data
dat_annmax = combine(dat_ma -> dat_ma[argmax(dat_ma.residual), :], groupby(DataFrames.transform(dat_ma, :datetime => x->year.(x)), :datetime_function))
delete!(dat_annmax, nrow(dat_annmax)) # delete 2023; haven't seen much of that year yet
rename!(dat_annmax, :datetime_function => :Year)
select!(dat_annmax, [:Year, :residual])

# make plots
p1 = plot(
    dat_annmax.Year,
    dat_annmax.residual;
    xlabel="Year",
    ylabel="Annual Max Tide Level (mm)",
    label=false,
    marker=:circle,
    markersize=5,
    tickfontsize=16,
    guidefontsize=18
)
p2 = histogram(
    dat_annmax.residual,
    normalize=:pdf,
    orientation=:horizontal,
    label=:false,
    xlabel="PDF",
    xlims=(0, 0.006),
    ylabel="",
    yticks=[],
    xticks = [],
    tickfontsize=16,
    guidefontsize=18
)

l = @layout [a{0.7w} b{0.3w}]
plot(p1, p2; layout=l, link=:y, ylims=(1000, 1700), bottom_margin=5mm, left_margin=5mm)
plot!(size=(1000, 450))
Figure 2: Annual maxima surge data from the San Francisco, CA tide gauge.

Probability Model (Annual Maxima)

\[\begin{gather*} y_t \sim \text{GEV}(\mu, \sigma, \xi) \\ \mu \sim \mathcal{LogNormal}(7, 0.25) \\ \sigma \sim \mathcal{TN}(0, 100; 0, \infty) \\ \xi \sim \mathcal{N}(0, 0.1) \end{gather*}\]

Prior Predictive Check

Code
# sample from priors
μ = rand(LogNormal(7, 0.25), 1000)
σ = rand(truncated(Normal(0, 100), lower=0), 1000)
ξ = rand(Normal(0, 0.1), 1000)
# simulate
# define return periods and cmopute return levels for parameters
return_periods = 2:100
return_levels = zeros(1_000, length(return_periods))
for i in 1:1_000
    return_levels[i, :] = quantile.(GeneralizedExtremeValue(μ[i], σ[i], ξ[i]), 1 .- (1 ./ return_periods))
end

plt_prior_1 = plot(; ylabel="Return Level (m)", xlabel="Return Period (yrs)", tickfontsize=16, legendfontsize=18, guidefontsize=18, bottom_margin=10mm, left_margin=10mm, legend=:topleft)
for idx in 1:1_000
    label = idx == 1 ? "Prior" : false
    plot!(plt_prior_1, return_periods, return_levels[idx, :]; color=:black, alpha=0.1, label=label)
end
plt_prior_1
Figure 3: Prior predictive check for surge model.

Probabilistic Programming Languages

  • Rely on more advanced methods (e.g. Hamiltonian Monte Carlo) to draw samples more efficiently.
  • Use automatic differentiation to compute gradients.
  • Syntax closely resembles statistical model specification.
  • Examples:

Turing Model Specification

@model function sf_surge(y)
    ## pick priors
    μ ~ LogNormal(7, 0.25) # location
    σ ~ truncated(Normal(0, 100); lower=0) # scale
    ξ ~ Normal(0, 0.1) # shape

    ## likelihood
    y .~ GeneralizedExtremeValue(μ, σ, ξ)
end
sf_surge (generic function with 2 methods)

Sampling with Turing

surge_chain = let # variables defined in a let...end block are temporary
    model = sf_surge(dat_annmax.residual) # initialize model with data
    sampler = NUTS() # use the No-U-Turn Sampler; there are other options
    nsamples = 10_000
    sample(model, sampler, nsamples; drop_warmup=true)
end
summarystats(surge_chain)
Sampling   0%|                                          |  ETA: N/A
Info: Found initial step size
  ϵ = 0.0015625
Sampling   0%|▎                                         |  ETA: 0:16:48
Sampling   1%|▍                                         |  ETA: 0:08:23
Sampling   2%|▋                                         |  ETA: 0:05:35
Sampling   2%|▉                                         |  ETA: 0:04:10
Sampling   2%|█                                         |  ETA: 0:03:20
Sampling   3%|█▎                                        |  ETA: 0:02:46
Sampling   4%|█▌                                        |  ETA: 0:02:21
Sampling   4%|█▋                                        |  ETA: 0:02:03
Sampling   4%|█▉                                        |  ETA: 0:01:49
Sampling   5%|██▏                                       |  ETA: 0:01:38
Sampling   6%|██▎                                       |  ETA: 0:01:29
Sampling   6%|██▌                                       |  ETA: 0:01:21
Sampling   6%|██▊                                       |  ETA: 0:01:14
Sampling   7%|███                                       |  ETA: 0:01:09
Sampling   8%|███▏                                      |  ETA: 0:01:04
Sampling   8%|███▍                                      |  ETA: 0:01:00
Sampling   8%|███▋                                      |  ETA: 0:00:56
Sampling   9%|███▊                                      |  ETA: 0:00:52
Sampling  10%|████                                      |  ETA: 0:00:50
Sampling  10%|████▎                                     |  ETA: 0:00:47
Sampling  10%|████▍                                     |  ETA: 0:00:44
Sampling  11%|████▋                                     |  ETA: 0:00:42
Sampling  12%|████▉                                     |  ETA: 0:00:40
Sampling  12%|█████                                     |  ETA: 0:00:38
Sampling  12%|█████▎                                    |  ETA: 0:00:37
Sampling  13%|█████▌                                    |  ETA: 0:00:35
Sampling  14%|█████▋                                    |  ETA: 0:00:34
Sampling  14%|█████▉                                    |  ETA: 0:00:32
Sampling  14%|██████▏                                   |  ETA: 0:00:31
Sampling  15%|██████▎                                   |  ETA: 0:00:30
Sampling  16%|██████▌                                   |  ETA: 0:00:29
Sampling  16%|██████▊                                   |  ETA: 0:00:28
Sampling  16%|██████▉                                   |  ETA: 0:00:27
Sampling  17%|███████▏                                  |  ETA: 0:00:26
Sampling  18%|███████▍                                  |  ETA: 0:00:25
Sampling  18%|███████▌                                  |  ETA: 0:00:24
Sampling  18%|███████▊                                  |  ETA: 0:00:23
Sampling  19%|████████                                  |  ETA: 0:00:23
Sampling  20%|████████▎                                 |  ETA: 0:00:22
Sampling  20%|████████▍                                 |  ETA: 0:00:21
Sampling  20%|████████▋                                 |  ETA: 0:00:21
Sampling  21%|████████▉                                 |  ETA: 0:00:20
Sampling  22%|█████████                                 |  ETA: 0:00:19
Sampling  22%|█████████▎                                |  ETA: 0:00:19
Sampling  22%|█████████▌                                |  ETA: 0:00:18
Sampling  23%|█████████▋                                |  ETA: 0:00:18
Sampling  24%|█████████▉                                |  ETA: 0:00:18
Sampling  24%|██████████▏                               |  ETA: 0:00:17
Sampling  24%|██████████▎                               |  ETA: 0:00:17
Sampling  25%|██████████▌                               |  ETA: 0:00:16
Sampling  26%|██████████▊                               |  ETA: 0:00:16
Sampling  26%|██████████▉                               |  ETA: 0:00:15
Sampling  26%|███████████▏                              |  ETA: 0:00:15
Sampling  27%|███████████▍                              |  ETA: 0:00:15
Sampling  28%|███████████▌                              |  ETA: 0:00:14
Sampling  28%|███████████▊                              |  ETA: 0:00:14
Sampling  28%|████████████                              |  ETA: 0:00:14
Sampling  29%|████████████▏                             |  ETA: 0:00:13
Sampling  30%|████████████▍                             |  ETA: 0:00:13
Sampling  30%|████████████▋                             |  ETA: 0:00:13
Sampling  30%|████████████▊                             |  ETA: 0:00:12
Sampling  31%|█████████████                             |  ETA: 0:00:12
Sampling  32%|█████████████▎                            |  ETA: 0:00:12
Sampling  32%|█████████████▌                            |  ETA: 0:00:12
Sampling  32%|█████████████▋                            |  ETA: 0:00:11
Sampling  33%|█████████████▉                            |  ETA: 0:00:11
Sampling  34%|██████████████▏                           |  ETA: 0:00:11
Sampling  34%|██████████████▎                           |  ETA: 0:00:11
Sampling  34%|██████████████▌                           |  ETA: 0:00:10
Sampling  35%|██████████████▊                           |  ETA: 0:00:10
Sampling  36%|██████████████▉                           |  ETA: 0:00:10
Sampling  36%|███████████████▏                          |  ETA: 0:00:10
Sampling  36%|███████████████▍                          |  ETA: 0:00:10
Sampling  37%|███████████████▌                          |  ETA: 0:00:09
Sampling  38%|███████████████▊                          |  ETA: 0:00:09
Sampling  38%|████████████████                          |  ETA: 0:00:09
Sampling  38%|████████████████▏                         |  ETA: 0:00:09
Sampling  39%|████████████████▍                         |  ETA: 0:00:09
Sampling  40%|████████████████▋                         |  ETA: 0:00:08
Sampling  40%|████████████████▊                         |  ETA: 0:00:08
Sampling  40%|█████████████████                         |  ETA: 0:00:08
Sampling  41%|█████████████████▎                        |  ETA: 0:00:08
Sampling  42%|█████████████████▍                        |  ETA: 0:00:08
Sampling  42%|█████████████████▋                        |  ETA: 0:00:08
Sampling  42%|█████████████████▉                        |  ETA: 0:00:08
Sampling  43%|██████████████████                        |  ETA: 0:00:07
Sampling  44%|██████████████████▎                       |  ETA: 0:00:07
Sampling  44%|██████████████████▌                       |  ETA: 0:00:07
Sampling  44%|██████████████████▊                       |  ETA: 0:00:07
Sampling  45%|██████████████████▉                       |  ETA: 0:00:07
Sampling  46%|███████████████████▏                      |  ETA: 0:00:07
Sampling  46%|███████████████████▍                      |  ETA: 0:00:07
Sampling  46%|███████████████████▌                      |  ETA: 0:00:06
Sampling  47%|███████████████████▊                      |  ETA: 0:00:06
Sampling  48%|████████████████████                      |  ETA: 0:00:06
Sampling  48%|████████████████████▏                     |  ETA: 0:00:06
Sampling  48%|████████████████████▍                     |  ETA: 0:00:06
Sampling  49%|████████████████████▋                     |  ETA: 0:00:06
Sampling  50%|████████████████████▊                     |  ETA: 0:00:06
Sampling  50%|█████████████████████                     |  ETA: 0:00:06
Sampling  50%|█████████████████████▎                    |  ETA: 0:00:06
Sampling  51%|█████████████████████▍                    |  ETA: 0:00:05
Sampling  52%|█████████████████████▋                    |  ETA: 0:00:05
Sampling  52%|█████████████████████▉                    |  ETA: 0:00:05
Sampling  52%|██████████████████████                    |  ETA: 0:00:05
Sampling  53%|██████████████████████▎                   |  ETA: 0:00:05
Sampling  54%|██████████████████████▌                   |  ETA: 0:00:05
Sampling  54%|██████████████████████▋                   |  ETA: 0:00:05
Sampling  55%|██████████████████████▉                   |  ETA: 0:00:05
Sampling  55%|███████████████████████▏                  |  ETA: 0:00:05
Sampling  56%|███████████████████████▎                  |  ETA: 0:00:05
Sampling  56%|███████████████████████▌                  |  ETA: 0:00:05
Sampling  56%|███████████████████████▊                  |  ETA: 0:00:04
Sampling  57%|████████████████████████                  |  ETA: 0:00:04
Sampling  57%|████████████████████████▏                 |  ETA: 0:00:04
Sampling  58%|████████████████████████▍                 |  ETA: 0:00:04
Sampling  58%|████████████████████████▋                 |  ETA: 0:00:04
Sampling  59%|████████████████████████▊                 |  ETA: 0:00:04
Sampling  60%|█████████████████████████                 |  ETA: 0:00:04
Sampling  60%|█████████████████████████▎                |  ETA: 0:00:04
Sampling  60%|█████████████████████████▍                |  ETA: 0:00:04
Sampling  61%|█████████████████████████▋                |  ETA: 0:00:04
Sampling  62%|█████████████████████████▉                |  ETA: 0:00:04
Sampling  62%|██████████████████████████                |  ETA: 0:00:04
Sampling  62%|██████████████████████████▎               |  ETA: 0:00:03
Sampling  63%|██████████████████████████▌               |  ETA: 0:00:03
Sampling  64%|██████████████████████████▋               |  ETA: 0:00:03
Sampling  64%|██████████████████████████▉               |  ETA: 0:00:03
Sampling  64%|███████████████████████████▏              |  ETA: 0:00:03
Sampling  65%|███████████████████████████▎              |  ETA: 0:00:03
Sampling  66%|███████████████████████████▌              |  ETA: 0:00:03
Sampling  66%|███████████████████████████▊              |  ETA: 0:00:03
Sampling  66%|███████████████████████████▉              |  ETA: 0:00:03
Sampling  67%|████████████████████████████▏             |  ETA: 0:00:03
Sampling  68%|████████████████████████████▍             |  ETA: 0:00:03
Sampling  68%|████████████████████████████▌             |  ETA: 0:00:03
Sampling  68%|████████████████████████████▊             |  ETA: 0:00:03
Sampling  69%|█████████████████████████████             |  ETA: 0:00:03
Sampling  70%|█████████████████████████████▎            |  ETA: 0:00:03
Sampling  70%|█████████████████████████████▍            |  ETA: 0:00:03
Sampling  70%|█████████████████████████████▋            |  ETA: 0:00:02
Sampling  71%|█████████████████████████████▉            |  ETA: 0:00:02
Sampling  72%|██████████████████████████████            |  ETA: 0:00:02
Sampling  72%|██████████████████████████████▎           |  ETA: 0:00:02
Sampling  72%|██████████████████████████████▌           |  ETA: 0:00:02
Sampling  73%|██████████████████████████████▋           |  ETA: 0:00:02
Sampling  74%|██████████████████████████████▉           |  ETA: 0:00:02
Sampling  74%|███████████████████████████████▏          |  ETA: 0:00:02
Sampling  74%|███████████████████████████████▎          |  ETA: 0:00:02
Sampling  75%|███████████████████████████████▌          |  ETA: 0:00:02
Sampling  76%|███████████████████████████████▊          |  ETA: 0:00:02
Sampling  76%|███████████████████████████████▉          |  ETA: 0:00:02
Sampling  76%|████████████████████████████████▏         |  ETA: 0:00:02
Sampling  77%|████████████████████████████████▍         |  ETA: 0:00:02
Sampling  78%|████████████████████████████████▌         |  ETA: 0:00:02
Sampling  78%|████████████████████████████████▊         |  ETA: 0:00:02
Sampling  78%|█████████████████████████████████         |  ETA: 0:00:02
Sampling  79%|█████████████████████████████████▏        |  ETA: 0:00:02
Sampling  80%|█████████████████████████████████▍        |  ETA: 0:00:02
Sampling  80%|█████████████████████████████████▋        |  ETA: 0:00:02
Sampling  80%|█████████████████████████████████▊        |  ETA: 0:00:01
Sampling  81%|██████████████████████████████████        |  ETA: 0:00:01
Sampling  82%|██████████████████████████████████▎       |  ETA: 0:00:01
Sampling  82%|██████████████████████████████████▌       |  ETA: 0:00:01
Sampling  82%|██████████████████████████████████▋       |  ETA: 0:00:01
Sampling  83%|██████████████████████████████████▉       |  ETA: 0:00:01
Sampling  84%|███████████████████████████████████▏      |  ETA: 0:00:01
Sampling  84%|███████████████████████████████████▎      |  ETA: 0:00:01
Sampling  84%|███████████████████████████████████▌      |  ETA: 0:00:01
Sampling  85%|███████████████████████████████████▊      |  ETA: 0:00:01
Sampling  86%|███████████████████████████████████▉      |  ETA: 0:00:01
Sampling  86%|████████████████████████████████████▏     |  ETA: 0:00:01
Sampling  86%|████████████████████████████████████▍     |  ETA: 0:00:01
Sampling  87%|████████████████████████████████████▌     |  ETA: 0:00:01
Sampling  88%|████████████████████████████████████▊     |  ETA: 0:00:01
Sampling  88%|█████████████████████████████████████     |  ETA: 0:00:01
Sampling  88%|█████████████████████████████████████▏    |  ETA: 0:00:01
Sampling  89%|█████████████████████████████████████▍    |  ETA: 0:00:01
Sampling  90%|█████████████████████████████████████▋    |  ETA: 0:00:01
Sampling  90%|█████████████████████████████████████▊    |  ETA: 0:00:01
Sampling  90%|██████████████████████████████████████    |  ETA: 0:00:01
Sampling  91%|██████████████████████████████████████▎   |  ETA: 0:00:01
Sampling  92%|██████████████████████████████████████▍   |  ETA: 0:00:01
Sampling  92%|██████████████████████████████████████▋   |  ETA: 0:00:01
Sampling  92%|██████████████████████████████████████▉   |  ETA: 0:00:01
Sampling  93%|███████████████████████████████████████   |  ETA: 0:00:00
Sampling  94%|███████████████████████████████████████▎  |  ETA: 0:00:00
Sampling  94%|███████████████████████████████████████▌  |  ETA: 0:00:00
Sampling  94%|███████████████████████████████████████▊  |  ETA: 0:00:00
Sampling  95%|███████████████████████████████████████▉  |  ETA: 0:00:00
Sampling  96%|████████████████████████████████████████▏ |  ETA: 0:00:00
Sampling  96%|████████████████████████████████████████▍ |  ETA: 0:00:00
Sampling  96%|████████████████████████████████████████▌ |  ETA: 0:00:00
Sampling  97%|████████████████████████████████████████▊ |  ETA: 0:00:00
Sampling  98%|█████████████████████████████████████████ |  ETA: 0:00:00
Sampling  98%|█████████████████████████████████████████▏|  ETA: 0:00:00
Sampling  98%|█████████████████████████████████████████▍|  ETA: 0:00:00
Sampling  99%|█████████████████████████████████████████▋|  ETA: 0:00:00
Sampling 100%|█████████████████████████████████████████▊|  ETA: 0:00:00
Sampling 100%|██████████████████████████████████████████| Time: 0:00:06
Sampling 100%|██████████████████████████████████████████| Time: 0:00:06
Summary Statistics
  parameters        mean       std      mcse    ess_bulk    ess_tail      rhat     Symbol     Float64   Float64   Float64     Float64     Float64   Float64 ⋯

           μ   1258.8171    5.6485    0.0607   8634.0238   7843.7165    1.0003 ⋯
           σ     57.5254    4.1645    0.0528   6235.1999   6852.9548    0.9999 ⋯
           ξ      0.0161    0.0517    0.0007   5967.6089   5948.6467    1.0000 ⋯
                                                                1 column omitted

Sampling Visualization

Code
plot(surge_chain, size=(1200, 500), left_margin=5mm, bottom_margin=5mm)
Figure 4: Sampler visualization for surge chain

Optimizing with Turing

We can also use Turing.jl along with Optim.jl to get the MLE and MAP.

MLE

mle_surge = optimize(sf_surge(dat_annmax.residual), MLE())
coeftable(mle_surge)
Coef. Std. Error z Pr(> z )
μ 1258.71 5.61428 224.198 0.0 1247.71 1269.71
σ 56.2665 4.08661 13.7685 3.94289e-43 48.2569 64.2761
ξ 0.0171937 0.0624531 0.275306 0.783081 -0.105212 0.139599

MAP

map_surge = optimize(sf_surge(dat_annmax.residual), MAP())
coeftable(map_surge)
Warning:     Optimization did not converge! You may need to correct your model or adjust the
    Optim parameters.
@ TuringOptimExt ~/.julia/packages/Turing/1Egt9/ext/TuringOptimExt.jl:177
Coef. Std. Error z Pr(> z ) Lower 95%
μ 615.256 NaN NaN NaN NaN NaN Negative variance
σ 47.7073 0.678911 70.2703 0.0 46.3766 49.0379
ξ -0.0538472 0.000385557 -139.661 0.0 -0.0546028 -0.0530915

Posterior Visualization

Code
p1 = histogram(surge_chain[:μ], label="Samples", normalize=:pdf, legend=:topleft, xlabel=L"μ", ylabel=L"p(μ|y)")
p2 = histogram(surge_chain[:σ], label="Samples", normalize=:pdf, legend=:topleft, xlabel=L"σ", ylabel=L"p(σ|y)")
p3 = histogram(surge_chain[:ξ], label="Samples", normalize=:pdf, legend=:topleft, xlabel=L"σ", ylabel=L"p(σ|y)")
p = plot(p1, p2, p3, tickfontsize=16, guidefontsize=18, legendfontsize=18, left_margin=10mm, bottom_margin=10mm, layout = @layout [a b c])
vline!(p, mean(surge_chain)[:, 2]', color=:purple, linewidth=3, label="Posterior Mean")
plot!(p, size=(1200, 450))
Figure 5: Posterior visualization for surge chain

Correlations

Code
p1 = histogram2d(surge_chain[:μ], surge_chain[:σ], normalize=:pdf, legend=false, xlabel=L"μ", ylabel=L"σ")
p2 = histogram2d(surge_chain[:μ], surge_chain[:ξ], normalize=:pdf, legend=false, xlabel=L"μ", ylabel=L"ξ")
p3 = histogram2d(surge_chain[:σ], surge_chain[:ξ], normalize=:pdf, legend=false, xlabel=L"σ", ylabel=L"ξ")
p = plot(p1, p2, p3, tickfontsize=16, guidefontsize=18, left_margin=5mm, bottom_margin=5mm, layout = @layout [a b c])
plot!(p, size=(1200, 450))
Figure 6: Posterior correlations

Posterior Predictive Checks

Code
plt_rt = plot(; ylabel="Return Level (m)", xlabel="Return Period (yrs)", tickfontsize=16, legendfontsize=18, guidefontsize=18, bottom_margin=10mm, left_margin=10mm, legend=:topleft)
for idx in 1:1000
    μ = surge_chain[:μ][idx]
    σ = surge_chain[:σ][idx]
    ξ = surge_chain[:ξ][idx]
    return_levels[idx, :] = quantile.(GeneralizedExtremeValue(μ, σ, ξ), 1 .- (1 ./ return_periods))
    label = idx == 1 ? "Posterior" : false
    plot!(plt_rt, return_periods, return_levels[idx, :]; color=:black, alpha=0.05, label=label, linewidth=0.5)
end
# plot return level quantiles
rl_q = mapslices(col -> quantile(col, [0.025, 0.5, 0.975]), return_levels, dims=1)
plot!(plt_rt, return_periods, rl_q[[1,3], :]', color=:green, linewidth=2, label="95% CI")
plot!(plt_rt, return_periods, rl_q[2, :], color=:red, linewidth=2, label="Posterior Median")
# plot data
scatter!(plt_rt, return_periods, quantile(dat_annmax.residual, 1 .- (1 ./ return_periods)), label="Data", color=:black)
plot!(plt_rt, size=(1200, 500))
plt_rt
Figure 7: Posterior predictive checks

Multiple Chains

surge_chain = let # variables defined in a let...end block are temporary
    model = sf_surge(dat_annmax.residual) # initialize model with data
    sampler = NUTS() # use the No-U-Turn Sampler; there are other options
    nsamples = 10_000
    nchains = 4
    sample(model, sampler, MCMCThreads(), nsamples, nchains; drop_warmup=true)
end
gelmandiag(surge_chain)
Warning: Only a single thread available: MCMC chains are not sampled in parallel
@ AbstractMCMC ~/.julia/packages/AbstractMCMC/kwj9g/src/sample.jl:384
Sampling (1 thread)   0%|                               |  ETA: N/A
Info: Found initial step size
  ϵ = 0.000390625
Info: Found initial step size
  ϵ = 0.00078125
Sampling (1 thread)  25%|███████▊                       |  ETA: 0:00:10
Sampling (1 thread)  50%|███████████████▌               |  ETA: 0:00:04
Info: Found initial step size
  ϵ = 0.0015625
Info: Found initial step size
  ϵ = 0.00625
Sampling (1 thread)  75%|███████████████████████▎       |  ETA: 0:00:02
Sampling (1 thread) 100%|███████████████████████████████| Time: 0:00:06
Sampling (1 thread) 100%|███████████████████████████████| Time: 0:00:06
Gelman, Rubin, and Brooks diagnostic
  parameters      psrf    psrfci 
      Symbol   Float64   Float64 

           μ    1.0000    1.0000
           σ    1.0000    1.0001
           ξ    1.0000    1.0000

Plotting Multiple Chains

Code
plot(surge_chain)
plot!(size=(1200, 500))
Figure 8: Sampler visualization for multiple surge chains

Key Points and Upcoming Schedule

Key Points (Convergence)

  • Must rely on “accumulation of evidence” from heuristics for determination about convergence to stationary distribution.
  • Transient portion of chain: Meh. Some people worry about this too much. Discard or run the chain longer.
  • Parallelizing solves few problems, but running multiple chains can be useful for diagnostics.

Next Classes

Monday: MCMC Lab (No exercises these weeks)

Next Wednesday: Literature Presentations (email slides by 9pm Tuesday night).

Assessments

  • Homework 3: Due 3/22

References

References

Gelman, A., & Rubin, D. B. (1992). Inference from Iterative Simulation Using Multiple Simulations. Stat. Sci., 7, 457–511. https://doi.org/10.1214/ss/1177011136