1 AR(1) model

Let us assume that time-series observations \(y_1,\ldots,y_n\) are modeled via a autoregressive (AR) model of order one, ie. AR(1): \[ y_t|y_{t-1},\theta \sim N(\mu+\phi y_{t-1},\sigma^2), \] for \(t=2,\ldots,n\) and \(\theta=(\mu,\phi,\sigma^2)\). Inference is conditional on the value of \(y_1\) due to the lag structure of the AR(1) process. However, some of the observations are missing, as in the following simulated example, where observations \(t=65,\ldots,75\) are missing.

set.seed(31415)
mu  = 0.05
phi = 0.95
sig = 0.25
n   = 100
y   = rep(mu/(1-phi),n)
for (t in 2:n)
  y[t] = mu + phi*y[t-1]+rnorm(1,0,sig)
y.true = y
par.true = c(mu,phi,sig)

a=65
b=75
midpoint = trunc((a+b)/2)
y[a:b]=(y[a-1]+y[b+1])/2

par(mfrow=c(1,1))
ts.plot(y.true,xlab="Time",ylab="Observations",lwd=2)
lines(y,col=2,lwd=2)
abline(v=a,lty=2)
abline(v=b,lty=2)
legend("topleft",legend=c("True data","Observed data"),col=1:2,lty=1,lwd=2,bty="n")

2 Gibbs sampler

Assuming a noninformative prior for the parameters \(\mu,\phi,\sigma^2,y_a,y_{a+1},\ldots,y_b\), ie. \[ p(\mu,\phi,\sigma^2,y_a,y_{a+1},\ldots,y_b) \propto \frac{1}{\sigma^2}, \] such that posterior inference is feasible via Markov chain Monte Carlo through the Gibbs sampler. More preciselly, we can easily the full conditionals for each one of the parameters.

2.1 Full conditional of \(\mu\)

To sample \(\mu\) from its full conditional, we first define \(z_t=y_t-\phi y_{t-1}\), for \(t=2,\ldots,n\). Then, \[ p(\mu|\mbox{all}) \propto \exp\left\{-\frac{0.5}{\sigma^2} \sum_{i=1}^n (z_t-\mu)^2 \right\} \propto \exp\left\{-\frac{0.5}{\sigma^2/(n-1)} (\mu^2 - 2\mu {\bar z}) \right\}, \] where \({\bar z}=\sum_{t=2}^n (y_t-\phi y_{t-1})/(n-1)\). Therefore, the full conditional of \(\mu\) is Gaussian: \[ (\mu|\mbox{all}) \sim N({\bar z},\sigma^2/(n-1)). \]

2.2 Full conditional of \(\phi\)

To sample \(\phi\) from its full conditional, we first define \(z_t=y_t-\mu\), for \(t=2,\ldots,n\). Then, \[ p(\phi|\mbox{all}) \propto \exp\left\{-\frac{0.5}{\sigma^2} \sum_{i=1}^n (z_t-\phi y_t)^2 \right\} \propto \exp\left\{-\frac{0.5}{\sigma^2/(n-1)} \left(\phi^2\sum_{t=1}^n z_t- 2\phi\sum_{i=2}^n z_t y_{t-1}\right) \right\}. \] Therefore, the full conditional of \(\phi\) is also Gaussian: \[ (\phi|\mbox{all}) \sim N\left( \frac{\sum_{t=2}^n (y_t-\mu)y_{t-1}}{\sum_{t=2}^n y_{t-1}^2},\frac{\sigma^2}{\sum_{t=2}^n y_{t-1}^2}\right). \]

2.3 Full conditional of \(\sigma^2\)

The full conditional distribution of \(\sigma^2\) is the simplest to derive \[ p(\sigma^2|\mbox{all}) \propto \sigma^{-2} \exp\left\{-\frac{0.5}{\sigma^2} \sum_{t=2}^n (y_t-\mu-\phi y_{t-1})^2\right\}, \] which, as a function of \(\sigma^2\), is the kernal of an inverse gamma distribution with parameters \(n+1/2\) and \(\sum_{t=2}^n (y_t-\mu-\phi y_{t-1})^2/2\): \[ (\sigma^2|\mbox{all}) \sim IG\left(\frac{n+1}{2},\frac{\sum_{t=2}^n (y_t-\mu-\phi y_{t-1})^2}{2}\right) \]

2.4 Full conditional of missing \(y\)s

The full conditional for the missing \(y_t\) is given by

\[\begin{eqnarray*} p(y_t|\mbox{all}) &\propto& p(y_t|y_{t-1},\theta)p(y_{t+1}|y_t,\theta)\\ &\propto& \exp\left\{-\frac{0.5}{\sigma^2} \left[ (y_t-(\mu+\phi y_{t-1})^2+((y_{t+1}-\mu)-\phi y_t)^2 \right]\right\}\\ &\propto& \exp \left\{-\frac{0.5}{\sigma^2} \left[ y_t^2 - 2 y_t(\mu+\phi y_{t-1}) + \phi^2 y_t^2 - 2y_t\phi(y_{t+1}-\mu)\right] \right\}\\ &\propto& \exp \left\{-\frac{0.5}{\sigma^2} \left[ (1+\phi^2)y_t^2 - 2 y_t(\mu+\phi y_{t-1}+\phi(y_{t+1}-\mu))\right] \right\}, \end{eqnarray*}\] which is a Gaussian kernel with mean and variance \[ \frac{\mu(1-\phi) + \phi(y_{t-1}+y_{t+1})}{1+\phi^2} \ \ \ \mbox{and} \ \ \ \frac{\sigma^2}{(1+\phi^2)}, \] respectively.

burnin = 10000
M      = 2000
skip   = 100
niter  = burnin+M*skip
draws  = matrix(0,niter,b-a+4)
for (iter in 1:niter){
  # Sampling mu
  z       = y[2:n]-phi*y[1:(n-1)]
  mu      = rnorm(1,mean(z),sig/sqrt(n-1))
  # Sampling phi
  var.phi = sig^2/sum(y[1:(n-1)]^2)
  mean.phi = var.phi*sum((y[2:n]-mu)*y[1:(n-1)])/sig^2
  phi = rnorm(1,mean.phi,sqrt(var.phi))
  # Sampling sigma2
  par1 = n + 1
  par2 = sum((y[2:n]-mu-phi*y[1:(n-1)])^2)
  sig  = sqrt(1/rgamma(1,par1/2,par2/2))
  # Sampling missing observations
  for (t in a:b)
    y[t] = rnorm(1,(mu*(1-phi)+phi*(y[t-1]+y[t+1]))/(1+phi^2),sig/sqrt(1+phi^2))
  draws[iter,] = c(y[a:b],phi,sig,mu)
}
ind  = seq(burnin+1,niter,by=skip)
mus  = draws[ind,b-a+4]
phis = draws[ind,b-a+2]
sigs = draws[ind,b-a+3]
ymid = draws[ind,midpoint-a+1]

2.5 Posterior summaries

par(mfrow=c(3,4))
ts.plot(mus,xlab="Iterations",ylab="",main=expression(mu))
ts.plot(phis,xlab="Iterations",ylab="",main=expression(phi))
ts.plot(sigs,xlab="Iterations",ylab="",main=expression(sigma))
ts.plot(ymid,xlab="Iterations",ylab="",main=paste("y[",midpoint,"]",sep=""))
acf(mus,main="")
acf(phis,main="")
acf(sigs,main="")
acf(ymid,main="")
hist(mus,prob=TRUE,xlab="",main="");abline(v=par.true[1],col=2,lwd=2)
hist(phis,prob=TRUE,xlab="",main="");abline(v=par.true[2],col=2,lwd=2)
hist(sigs,prob=TRUE,xlab="",main="");abline(v=par.true[3],col=2,lwd=2)
hist(ymid,prob=TRUE,xlab="",main="");abline(v=y.true[midpoint],col=2,lwd=2)

2.6 Posterior for the missing points

ys = draws[,1:(b-a+1)]
qy = t(apply(ys,2,quantile,c(0.05,0.5,0.95)))

par(mfrow=c(1,1))
plot(y.true,ylim=range(y.true,draws[,1:(b-a+1)]),xlab="Time",ylab="Observations")
abline(v=a,lty=2)
abline(v=b,lty=2)
for (i in 1:M)
  lines(a:b,draws[i,1:(b-a+1)],col=grey(0.8))
points(a:b,y.true[a:b],pch=16)
lines(a:b,qy[,1],col=2,lwd=2)
points(a:b,qy[,2],col=2,pch=16)
lines(a:b,qy[,3],col=2,lwd=2)
lines(y.true)

LS0tCnRpdGxlOiAiQVIoMSkgd2l0aCBtaXNzaW5nIgpzdWJ0aXRsZTogIkRhdGEgYXVnbWVudGF0aW9uIgphdXRob3I6ICJIZWRpYmVydCBGcmVpdGFzIExvcGVzIgpkYXRlOiAiYHIgU3lzLkRhdGUoKWAiCm91dHB1dDoKICBodG1sX2RvY3VtZW50OgogICAgdGhlbWU6IHBhcGVyCiAgICBoaWdobGlnaHQ6IHB5Z21lbnRzCiAgICB0b2M6IHRydWUKICAgIHRvY19kZXB0aDogMwogICAgdG9jX2NvbGxhcHNlZDogdHJ1ZQogICAgdG9jX2Zsb2F0OiB0cnVlCiAgICBjb2RlX2Rvd25sb2FkOiB0cnVlCiAgICBudW1iZXJfc2VjdGlvbnM6IHRydWUKLS0tCgoKIyBBUigxKSBtb2RlbApMZXQgdXMgYXNzdW1lIHRoYXQgdGltZS1zZXJpZXMgb2JzZXJ2YXRpb25zICR5XzEsXGxkb3RzLHlfbiQgYXJlIG1vZGVsZWQgdmlhIGEgYXV0b3JlZ3Jlc3NpdmUgKEFSKSBtb2RlbCBvZiBvcmRlciBvbmUsIGllLiBBUigxKToKJCQKeV90fHlfe3QtMX0sXHRoZXRhIFxzaW0gTihcbXUrXHBoaSB5X3t0LTF9LFxzaWdtYV4yKSwKJCQKZm9yICR0PTIsXGxkb3RzLG4kIGFuZCAkXHRoZXRhPShcbXUsXHBoaSxcc2lnbWFeMikkLiAgSW5mZXJlbmNlIGlzIGNvbmRpdGlvbmFsIG9uIHRoZSB2YWx1ZSBvZiAkeV8xJCBkdWUgdG8gdGhlIGxhZyBzdHJ1Y3R1cmUgb2YgdGhlIEFSKDEpIHByb2Nlc3MuICBIb3dldmVyLCBzb21lIG9mIHRoZSBvYnNlcnZhdGlvbnMgYXJlICBtaXNzaW5nLCBhcyBpbiB0aGUgZm9sbG93aW5nIHNpbXVsYXRlZCBleGFtcGxlLCB3aGVyZSBvYnNlcnZhdGlvbnMgJHQ9NjUsXGxkb3RzLDc1JCBhcmUgbWlzc2luZy4KCmBgYHtyIGZpZy5hbGlnbj0nY2VudGVyJywgZmlnLndpZHRoPTgsIGZpZy5oZWlnaHQ9NX0Kc2V0LnNlZWQoMzE0MTUpCm11ICA9IDAuMDUKcGhpID0gMC45NQpzaWcgPSAwLjI1Cm4gICA9IDEwMAp5ICAgPSByZXAobXUvKDEtcGhpKSxuKQpmb3IgKHQgaW4gMjpuKQogIHlbdF0gPSBtdSArIHBoaSp5W3QtMV0rcm5vcm0oMSwwLHNpZykKeS50cnVlID0geQpwYXIudHJ1ZSA9IGMobXUscGhpLHNpZykKCmE9NjUKYj03NQptaWRwb2ludCA9IHRydW5jKChhK2IpLzIpCnlbYTpiXT0oeVthLTFdK3lbYisxXSkvMgoKcGFyKG1mcm93PWMoMSwxKSkKdHMucGxvdCh5LnRydWUseGxhYj0iVGltZSIseWxhYj0iT2JzZXJ2YXRpb25zIixsd2Q9MikKbGluZXMoeSxjb2w9Mixsd2Q9MikKYWJsaW5lKHY9YSxsdHk9MikKYWJsaW5lKHY9YixsdHk9MikKbGVnZW5kKCJ0b3BsZWZ0IixsZWdlbmQ9YygiVHJ1ZSBkYXRhIiwiT2JzZXJ2ZWQgZGF0YSIpLGNvbD0xOjIsbHR5PTEsbHdkPTIsYnR5PSJuIikKYGBgCgojIEdpYmJzIHNhbXBsZXIKQXNzdW1pbmcgYSBub25pbmZvcm1hdGl2ZSBwcmlvciBmb3IgdGhlIHBhcmFtZXRlcnMgJFxtdSxccGhpLFxzaWdtYV4yLHlfYSx5X3thKzF9LFxsZG90cyx5X2IkLCBpZS4KJCQKcChcbXUsXHBoaSxcc2lnbWFeMix5X2EseV97YSsxfSxcbGRvdHMseV9iKSBccHJvcHRvIFxmcmFjezF9e1xzaWdtYV4yfSwKJCQKc3VjaCB0aGF0IHBvc3RlcmlvciBpbmZlcmVuY2UgaXMgZmVhc2libGUgdmlhIE1hcmtvdiBjaGFpbiBNb250ZSBDYXJsbyB0aHJvdWdoIHRoZSBHaWJicyBzYW1wbGVyLiAgTW9yZSBwcmVjaXNlbGx5LCAgd2UgY2FuIGVhc2lseSB0aGUgZnVsbCBjb25kaXRpb25hbHMgZm9yIGVhY2ggb25lIG9mIHRoZSBwYXJhbWV0ZXJzLgoKIyMgRnVsbCBjb25kaXRpb25hbCBvZiAkXG11JApUbyBzYW1wbGUgJFxtdSQgZnJvbSBpdHMgZnVsbCBjb25kaXRpb25hbCwgd2UgZmlyc3QgZGVmaW5lICR6X3Q9eV90LVxwaGkgeV97dC0xfSQsIGZvciAkdD0yLFxsZG90cyxuJC4gIFRoZW4sCiQkCnAoXG11fFxtYm94e2FsbH0pIFxwcm9wdG8gXGV4cFxsZWZ0XHstXGZyYWN7MC41fXtcc2lnbWFeMn0gXHN1bV97aT0xfV5uICh6X3QtXG11KV4yIFxyaWdodFx9IFxwcm9wdG8KXGV4cFxsZWZ0XHstXGZyYWN7MC41fXtcc2lnbWFeMi8obi0xKX0gKFxtdV4yIC0gMlxtdSB7XGJhciB6fSkgXHJpZ2h0XH0sCiQkCndoZXJlICR7XGJhciB6fT1cc3VtX3t0PTJ9Xm4gKHlfdC1ccGhpIHlfe3QtMX0pLyhuLTEpJC4gIFRoZXJlZm9yZSwgIHRoZSBmdWxsIGNvbmRpdGlvbmFsIG9mICRcbXUkIGlzIEdhdXNzaWFuOgokJAooXG11fFxtYm94e2FsbH0pIFxzaW0gTih7XGJhciB6fSxcc2lnbWFeMi8obi0xKSkuCiQkCgojIyBGdWxsIGNvbmRpdGlvbmFsIG9mICRccGhpJApUbyBzYW1wbGUgJFxwaGkkIGZyb20gaXRzIGZ1bGwgY29uZGl0aW9uYWwsIHdlIGZpcnN0IGRlZmluZSAkel90PXlfdC1cbXUkLCBmb3IgJHQ9MixcbGRvdHMsbiQuICBUaGVuLAokJApwKFxwaGl8XG1ib3h7YWxsfSkgXHByb3B0byBcZXhwXGxlZnRcey1cZnJhY3swLjV9e1xzaWdtYV4yfSBcc3VtX3tpPTF9Xm4gKHpfdC1ccGhpIHlfdCleMiBccmlnaHRcfSBccHJvcHRvClxleHBcbGVmdFx7LVxmcmFjezAuNX17XHNpZ21hXjIvKG4tMSl9IFxsZWZ0KFxwaGleMlxzdW1fe3Q9MX1ebiB6X3QtIDJccGhpXHN1bV97aT0yfV5uIHpfdCB5X3t0LTF9XHJpZ2h0KSBccmlnaHRcfS4KJCQKVGhlcmVmb3JlLCAgdGhlIGZ1bGwgY29uZGl0aW9uYWwgb2YgJFxwaGkkIGlzIGFsc28gR2F1c3NpYW46CiQkCihccGhpfFxtYm94e2FsbH0pIFxzaW0gTlxsZWZ0KCBcZnJhY3tcc3VtX3t0PTJ9Xm4gKHlfdC1cbXUpeV97dC0xfX17XHN1bV97dD0yfV5uIHlfe3QtMX1eMn0sXGZyYWN7XHNpZ21hXjJ9e1xzdW1fe3Q9Mn1ebiB5X3t0LTF9XjJ9XHJpZ2h0KS4KJCQKCiMjIEZ1bGwgY29uZGl0aW9uYWwgb2YgJFxzaWdtYV4yJAoKVGhlIGZ1bGwgY29uZGl0aW9uYWwgZGlzdHJpYnV0aW9uIG9mICRcc2lnbWFeMiQgaXMgdGhlIHNpbXBsZXN0IHRvIGRlcml2ZQokJApwKFxzaWdtYV4yfFxtYm94e2FsbH0pIFxwcm9wdG8gXHNpZ21hXnstMn0gXGV4cFxsZWZ0XHstXGZyYWN7MC41fXtcc2lnbWFeMn0gXHN1bV97dD0yfV5uICh5X3QtXG11LVxwaGkgeV97dC0xfSleMlxyaWdodFx9LAokJAp3aGljaCwgYXMgYSBmdW5jdGlvbiBvZiAkXHNpZ21hXjIkLCBpcyB0aGUga2VybmFsIG9mIGFuIGludmVyc2UgZ2FtbWEgZGlzdHJpYnV0aW9uIHdpdGggcGFyYW1ldGVycyAkbisxLzIkIGFuZCAkXHN1bV97dD0yfV5uICh5X3QtXG11LVxwaGkgeV97dC0xfSleMi8yJDoKJCQKKFxzaWdtYV4yfFxtYm94e2FsbH0pIFxzaW0gSUdcbGVmdChcZnJhY3tuKzF9ezJ9LFxmcmFje1xzdW1fe3Q9Mn1ebiAoeV90LVxtdS1ccGhpIHlfe3QtMX0pXjJ9ezJ9XHJpZ2h0KQokJAoKIyMgRnVsbCBjb25kaXRpb25hbCBvZiBtaXNzaW5nICR5JHMKVGhlIGZ1bGwgY29uZGl0aW9uYWwgZm9yIHRoZSBtaXNzaW5nICR5X3QkIGlzIGdpdmVuIGJ5CgoKXGJlZ2lue2VxbmFycmF5Kn0KcCh5X3R8XG1ib3h7YWxsfSkgJlxwcm9wdG8mIHAoeV90fHlfe3QtMX0sXHRoZXRhKXAoeV97dCsxfXx5X3QsXHRoZXRhKVxcCiZccHJvcHRvJiBcZXhwXGxlZnRcey1cZnJhY3swLjV9e1xzaWdtYV4yfSBcbGVmdFsKKHlfdC0oXG11K1xwaGkgeV97dC0xfSleMisoKHlfe3QrMX0tXG11KS1ccGhpIHlfdCleMgpccmlnaHRdXHJpZ2h0XH1cXAomXHByb3B0byYgXGV4cCBcbGVmdFx7LVxmcmFjezAuNX17XHNpZ21hXjJ9IApcbGVmdFsgeV90XjIgLSAyIHlfdChcbXUrXHBoaSB5X3t0LTF9KSArIFxwaGleMiB5X3ReMiAtIDJ5X3RccGhpKHlfe3QrMX0tXG11KVxyaWdodF0KXHJpZ2h0XH1cXAomXHByb3B0byYgXGV4cCBcbGVmdFx7LVxmcmFjezAuNX17XHNpZ21hXjJ9IApcbGVmdFsgKDErXHBoaV4yKXlfdF4yIC0gMiB5X3QoXG11K1xwaGkgeV97dC0xfStccGhpKHlfe3QrMX0tXG11KSlccmlnaHRdClxyaWdodFx9LApcZW5ke2VxbmFycmF5Kn0Kd2hpY2ggaXMgYSBHYXVzc2lhbiBrZXJuZWwgd2l0aCBtZWFuIGFuZCB2YXJpYW5jZQokJApcZnJhY3tcbXUoMS1ccGhpKSArIFxwaGkoeV97dC0xfSt5X3t0KzF9KX17MStccGhpXjJ9IFwgXCBcIFxtYm94e2FuZH0gXCBcIFwgClxmcmFje1xzaWdtYV4yfXsoMStccGhpXjIpfSwKJCQKcmVzcGVjdGl2ZWx5LgoKCgoKYGBge3J9CmJ1cm5pbiA9IDEwMDAwCk0gICAgICA9IDIwMDAKc2tpcCAgID0gMTAwCm5pdGVyICA9IGJ1cm5pbitNKnNraXAKZHJhd3MgID0gbWF0cml4KDAsbml0ZXIsYi1hKzQpCmZvciAoaXRlciBpbiAxOm5pdGVyKXsKICAjIFNhbXBsaW5nIG11CiAgeiAgICAgICA9IHlbMjpuXS1waGkqeVsxOihuLTEpXQogIG11ICAgICAgPSBybm9ybSgxLG1lYW4oeiksc2lnL3NxcnQobi0xKSkKICAjIFNhbXBsaW5nIHBoaQogIHZhci5waGkgPSBzaWdeMi9zdW0oeVsxOihuLTEpXV4yKQogIG1lYW4ucGhpID0gdmFyLnBoaSpzdW0oKHlbMjpuXS1tdSkqeVsxOihuLTEpXSkvc2lnXjIKICBwaGkgPSBybm9ybSgxLG1lYW4ucGhpLHNxcnQodmFyLnBoaSkpCiAgIyBTYW1wbGluZyBzaWdtYTIKICBwYXIxID0gbiArIDEKICBwYXIyID0gc3VtKCh5WzI6bl0tbXUtcGhpKnlbMToobi0xKV0pXjIpCiAgc2lnICA9IHNxcnQoMS9yZ2FtbWEoMSxwYXIxLzIscGFyMi8yKSkKICAjIFNhbXBsaW5nIG1pc3Npbmcgb2JzZXJ2YXRpb25zCiAgZm9yICh0IGluIGE6YikKICAgIHlbdF0gPSBybm9ybSgxLChtdSooMS1waGkpK3BoaSooeVt0LTFdK3lbdCsxXSkpLygxK3BoaV4yKSxzaWcvc3FydCgxK3BoaV4yKSkKICBkcmF3c1tpdGVyLF0gPSBjKHlbYTpiXSxwaGksc2lnLG11KQp9CmluZCAgPSBzZXEoYnVybmluKzEsbml0ZXIsYnk9c2tpcCkKbXVzICA9IGRyYXdzW2luZCxiLWErNF0KcGhpcyA9IGRyYXdzW2luZCxiLWErMl0Kc2lncyA9IGRyYXdzW2luZCxiLWErM10KeW1pZCA9IGRyYXdzW2luZCxtaWRwb2ludC1hKzFdCmBgYAoKIyMgUG9zdGVyaW9yIHN1bW1hcmllcwoKYGBge3IgZmlnLmFsaWduPSdjZW50ZXInLCBmaWcud2lkdGg9MTAsIGZpZy5oZWlnaHQ9MTB9CnBhcihtZnJvdz1jKDMsNCkpCnRzLnBsb3QobXVzLHhsYWI9Ikl0ZXJhdGlvbnMiLHlsYWI9IiIsbWFpbj1leHByZXNzaW9uKG11KSkKdHMucGxvdChwaGlzLHhsYWI9Ikl0ZXJhdGlvbnMiLHlsYWI9IiIsbWFpbj1leHByZXNzaW9uKHBoaSkpCnRzLnBsb3Qoc2lncyx4bGFiPSJJdGVyYXRpb25zIix5bGFiPSIiLG1haW49ZXhwcmVzc2lvbihzaWdtYSkpCnRzLnBsb3QoeW1pZCx4bGFiPSJJdGVyYXRpb25zIix5bGFiPSIiLG1haW49cGFzdGUoInlbIixtaWRwb2ludCwiXSIsc2VwPSIiKSkKYWNmKG11cyxtYWluPSIiKQphY2YocGhpcyxtYWluPSIiKQphY2Yoc2lncyxtYWluPSIiKQphY2YoeW1pZCxtYWluPSIiKQpoaXN0KG11cyxwcm9iPVRSVUUseGxhYj0iIixtYWluPSIiKTthYmxpbmUodj1wYXIudHJ1ZVsxXSxjb2w9Mixsd2Q9MikKaGlzdChwaGlzLHByb2I9VFJVRSx4bGFiPSIiLG1haW49IiIpO2FibGluZSh2PXBhci50cnVlWzJdLGNvbD0yLGx3ZD0yKQpoaXN0KHNpZ3MscHJvYj1UUlVFLHhsYWI9IiIsbWFpbj0iIik7YWJsaW5lKHY9cGFyLnRydWVbM10sY29sPTIsbHdkPTIpCmhpc3QoeW1pZCxwcm9iPVRSVUUseGxhYj0iIixtYWluPSIiKTthYmxpbmUodj15LnRydWVbbWlkcG9pbnRdLGNvbD0yLGx3ZD0yKQpgYGAKCiMjIFBvc3RlcmlvciBmb3IgdGhlIG1pc3NpbmcgcG9pbnRzCgpgYGB7ciBmaWcuYWxpZ249J2NlbnRlcicsIGZpZy53aWR0aD04LCBmaWcuaGVpZ2h0PTV9CnlzID0gZHJhd3NbLDE6KGItYSsxKV0KcXkgPSB0KGFwcGx5KHlzLDIscXVhbnRpbGUsYygwLjA1LDAuNSwwLjk1KSkpCgpwYXIobWZyb3c9YygxLDEpKQpwbG90KHkudHJ1ZSx5bGltPXJhbmdlKHkudHJ1ZSxkcmF3c1ssMTooYi1hKzEpXSkseGxhYj0iVGltZSIseWxhYj0iT2JzZXJ2YXRpb25zIikKYWJsaW5lKHY9YSxsdHk9MikKYWJsaW5lKHY9YixsdHk9MikKZm9yIChpIGluIDE6TSkKICBsaW5lcyhhOmIsZHJhd3NbaSwxOihiLWErMSldLGNvbD1ncmV5KDAuOCkpCnBvaW50cyhhOmIseS50cnVlW2E6Yl0scGNoPTE2KQpsaW5lcyhhOmIscXlbLDFdLGNvbD0yLGx3ZD0yKQpwb2ludHMoYTpiLHF5WywyXSxjb2w9MixwY2g9MTYpCmxpbmVzKGE6YixxeVssM10sY29sPTIsbHdkPTIpCmxpbmVzKHkudHJ1ZSkKYGBgCg==