Confidence Intervals

A confidence interval can be thought of as a vertical interval that we are reasonably confident the line representing our theoretical model passes through.

More precisely, a \(100\beta\%\) confidence interval given \(X = x\) is a range of \(Y\) values that we are \(100\beta\%\) confident will contain \(\mathrm{E}[Y | X=x] = \beta_0 + \beta_1 x\).

Such an interval accounts for the possible errors in the approximations of \(\hat\beta_0\) and \(\hat\beta_1\), but does not account for the uncertainty resulting from the noise term \(e\).

The \(100\beta\%\) confidence interval for \(\mathrm{E}[Y | X=x] = \beta_0 + \beta_1 x\) is given by:

\[\hat y \pm t_{(n-2, \alpha / 2)} \cdot s \sqrt{\frac{1}{n} + \frac{(x - \bar x)^2}{(n-1)s_X^2}} \] The \(\alpha\) in the formula above is given by \(\alpha = 1 - \beta\).

Prediction Intervals

A prediction interval can be thought of as a vertical interval that we are reasonably confident will contain the \(y\) coordinate of an observation with a given \(x\) coordinate.

More precisely, a \(100\beta\%\) prediction interval given \(X = x\) is a range of \(Y\) values that we are \(100\beta\%\) confident will contain \(y = \beta_0 + \beta_1 x + e\).

Such an interval accounts for the possible errors in the approximations of \(\hat\beta_0\) and \(\hat\beta_1\), as well as the uncertainty resulting from the noise term \(e\).

Prediction intervals are ALWAYS wider than confidence intervals.

The \(100\beta\%\) confidence interval for \(y = \beta_0 + \beta_1 x + e\) is given by:

\[\hat y \pm t_{(n-2, \alpha / 2)} \cdot s \sqrt{1 + \frac{1}{n} + \frac{(x - \bar x)^2}{(n-1)s_X^2}} \] The \(\alpha\) in the formula above is given by \(\alpha = 1 - \beta\).

Summary of Formulas

The \(100\beta\%\) confidence interval for \(\mathrm{E}[Y | X=x] = \beta_0 + \beta_1 x\) is given by:

\[\hat y \pm t_{(n-2, \alpha / 2)} \cdot s \sqrt{\frac{1}{n} + \frac{(x - \bar x)^2}{(n-1)s_X^2}} \] The \(100\beta\%\) confidence interval for \(y = \beta_0 + \beta_1 x + e\) is given by:

\[\hat y \pm t_{(n-2, \alpha / 2)} \cdot s \sqrt{1 + \frac{1}{n} + \frac{(x - \bar x)^2}{(n-1)s_X^2}} \] In each formula, we have that \(\alpha = 1 - \beta\).

Simulated Example

set.seed(1)
n = 10
x <- 8 + 1:n / 5
y <- 2*x + 3 + rnorm(n,0,0.8)
model <- lm(y~x)
          
plot(y ~ x, xlim=c(8,10.1), ylim=c(17,26), col="black", bg="red", pch=21, cex=1)
abline(model$coefficients, col="blue", lwd="2")

Let find the 95% confidence and prediction intervals for \(X=9\).

n = 10
x_ = 9
yhat = model$coefficients[1] + model$coefficients[2] * x_
s2 = sum((model$residuals)^2) / (n - 2)
s = sqrt(s2)
ci_sqrt = sqrt(1/n + (x_ - mean(x))^2 / ((n-1) * var(x)) )
pi_sqrt = sqrt(1 + 1/n + (x_ - mean(x))^2 / ((n-1) * var(x)) )
t = qt(0.975, n-2)
ci = c(yhat - t * s * ci_sqrt, yhat + t * s * ci_sqrt)
pi = c(yhat - t * s * pi_sqrt, yhat + t * s * pi_sqrt)
names(ci) = c('lower', 'upper')
names(pi) = c('lower', 'upper')
rbind(ci, pi)
      lower    upper
ci 20.60478 21.56296
pi 19.51630 22.65144

Let’s check our answer using the predict() function.

nd <- data.frame(x=9)
conf <- predict(model, interval="confidence", level=0.95, newdata=nd)
pred <- predict(model, interval="prediction", level=0.95, newdata=nd)
rbind(conf, pred)
       fit      lwr      upr
1 21.08387 20.60478 21.56296
1 21.08387 19.51630 22.65144

Example Using Pearson Data

We will now walk through an another example of using R to create prediction and confidence intervals. In this example, we will once again use the Pearson data set.

We start by loading the data and creating our model.

myData <- read.table("father_son.txt", sep="\t", header=TRUE)
mod <- lm(sheight ~ fheight, myData)
summary(mod)

Call:
lm(formula = sheight ~ fheight, data = myData)

Residuals:
    Min      1Q  Median      3Q     Max 
-8.8772 -1.5144 -0.0079  1.6285  8.9685 

Coefficients:
            Estimate Std. Error t value Pr(>|t|)    
(Intercept) 33.88660    1.83235   18.49   <2e-16 ***
fheight      0.51409    0.02705   19.01   <2e-16 ***
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

Residual standard error: 2.437 on 1076 degrees of freedom
Multiple R-squared:  0.2513,    Adjusted R-squared:  0.2506 
F-statistic: 361.2 on 1 and 1076 DF,  p-value: < 2.2e-16

We generate a scatter plot of the data, with the regression line included.

plot(myData$sheight ~ myData$fheight, pch=21, bg="cyan", col="black", cex=1,
     main="Scatter Plot", xlab="Father Height", ylab="Son Height")
abline(mod$coefficients, col="darkred", lwd=2)

The following code uses our model to predict the height of an adult male whose father is 5 feet tall.

nd1 = data.frame(fheight=60)
predict(mod, newdata = nd)
Error in eval(expr, envir, enclos) : object 'fheight' not found

Let’s create a 95% confidence interval for the height of an adult male whose father is 5 feet tall. Recall that this interval has a 95% chance of including the true population mean height for such individuals. It does NOT claim to contain the heights of 95% of these individuals.

predict(mod, newdata=data.frame(fheight=60), interval="confidence", level=.95)
       fit      lwr      upr
1 64.73219 64.29899 65.16538

If we want an interval that we believe will contain the heights of 95% of all adult males whose fathers are 5 feet tall, we need to consider a prediction interval instead.

predict(mod, data.frame(fheight=60), interval="predict", level=.95)
       fit      lwr      upr
1 64.73219 59.93166 69.53271

Let’s generate a prediction interval for the height of an adult male whose father is 6 feet tall.

predict(mod, data.frame(fheight=72), interval="predict", level=.95)
      fit      lwr      upr
1 70.9013 66.11267 75.68993

We can also use predict() to create predictions for several values of the predictor at once.

predict(mod, newdata=data.frame(fheight=c(60, 62, 64, 66, 68, 70, 72)), interval="predict", level=.95)
       fit      lwr      upr
1 64.73219 59.93166 69.53271
2 65.76037 60.96770 70.55304
3 66.78856 62.00140 71.57572
4 67.81674 63.03275 72.60074
5 68.84493 64.06175 73.62812
6 69.87312 65.08839 74.65785
7 70.90130 66.11267 75.68993

LS0tDQp0aXRsZTogIkxlc3NvbiAxMSAtIFByZWRpY3Rpb24gYW5kIENvbmZpZGVuY2UgSW50ZXJ2YWxzIg0KYXV0aG9yOiAiUm9iYmllIEJlYW5lIg0Kb3V0cHV0Og0KICBodG1sX25vdGVib29rOg0KICAgIHRoZW1lOiBmbGF0bHkNCiAgICB0b2M6IHRydWUNCiAgICB0b2NfZGVwdGg6IDINCi0tLQ0KDQojIENvbmZpZGVuY2UgSW50ZXJ2YWxzDQoNCkEgKipjb25maWRlbmNlIGludGVydmFsKiogY2FuIGJlIHRob3VnaHQgb2YgYXMgYSB2ZXJ0aWNhbCBpbnRlcnZhbCB0aGF0IHdlIGFyZSByZWFzb25hYmx5IGNvbmZpZGVudCB0aGUgbGluZSByZXByZXNlbnRpbmcgb3VyIHRoZW9yZXRpY2FsIG1vZGVsIHBhc3NlcyB0aHJvdWdoLiANCg0KTW9yZSBwcmVjaXNlbHksIGEgJDEwMFxiZXRhXCUkIGNvbmZpZGVuY2UgaW50ZXJ2YWwgZ2l2ZW4gJFggPSB4JCBpcyBhIHJhbmdlIG9mICRZJCB2YWx1ZXMgdGhhdCB3ZSBhcmUgJDEwMFxiZXRhXCUkIGNvbmZpZGVudCB3aWxsIGNvbnRhaW4gJFxtYXRocm17RX1bWSB8IFg9eF0gPSBcYmV0YV8wICsgXGJldGFfMSB4JC4gDQoNClN1Y2ggYW4gaW50ZXJ2YWwgYWNjb3VudHMgZm9yIHRoZSBwb3NzaWJsZSBlcnJvcnMgaW4gdGhlIGFwcHJveGltYXRpb25zIG9mICRcaGF0XGJldGFfMCQgYW5kICRcaGF0XGJldGFfMSQsIGJ1dCBkb2VzIG5vdCBhY2NvdW50IGZvciB0aGUgdW5jZXJ0YWludHkgcmVzdWx0aW5nIGZyb20gdGhlIG5vaXNlIHRlcm0gJGUkLiANCg0KVGhlICQxMDBcYmV0YVwlJCBjb25maWRlbmNlIGludGVydmFsIGZvciAkXG1hdGhybXtFfVtZIHwgWD14XSA9IFxiZXRhXzAgKyBcYmV0YV8xIHgkIGlzIGdpdmVuIGJ5Og0KDQokJFxoYXQgeSBccG0gdF97KG4tMiwgXGFscGhhIC8gMil9IFxjZG90IHMgXHNxcnR7XGZyYWN7MX17bn0gKyBcZnJhY3soeCAtIFxiYXIgeCleMn17KG4tMSlzX1heMn19ICQkDQpUaGUgJFxhbHBoYSQgaW4gdGhlIGZvcm11bGEgYWJvdmUgaXMgZ2l2ZW4gYnkgJFxhbHBoYSA9IDEgLSBcYmV0YSQuIA0KDQojIFByZWRpY3Rpb24gSW50ZXJ2YWxzDQoNCkEgKipwcmVkaWN0aW9uIGludGVydmFsKiogY2FuIGJlIHRob3VnaHQgb2YgYXMgYSB2ZXJ0aWNhbCBpbnRlcnZhbCB0aGF0IHdlIGFyZSByZWFzb25hYmx5IGNvbmZpZGVudCB3aWxsIGNvbnRhaW4gdGhlICR5JCBjb29yZGluYXRlIG9mIGFuIG9ic2VydmF0aW9uIHdpdGggYSBnaXZlbiAkeCQgY29vcmRpbmF0ZS4gDQoNCk1vcmUgcHJlY2lzZWx5LCBhICQxMDBcYmV0YVwlJCBwcmVkaWN0aW9uIGludGVydmFsIGdpdmVuICRYID0geCQgaXMgYSByYW5nZSBvZiAkWSQgdmFsdWVzIHRoYXQgd2UgYXJlICQxMDBcYmV0YVwlJCBjb25maWRlbnQgd2lsbCBjb250YWluICR5ID0gXGJldGFfMCArIFxiZXRhXzEgeCArIGUkLiANCg0KU3VjaCBhbiBpbnRlcnZhbCBhY2NvdW50cyBmb3IgdGhlIHBvc3NpYmxlIGVycm9ycyBpbiB0aGUgYXBwcm94aW1hdGlvbnMgb2YgJFxoYXRcYmV0YV8wJCBhbmQgJFxoYXRcYmV0YV8xJCwgYXMgd2VsbCBhcyB0aGUgdW5jZXJ0YWludHkgcmVzdWx0aW5nIGZyb20gdGhlIG5vaXNlIHRlcm0gJGUkLiANCg0KUHJlZGljdGlvbiBpbnRlcnZhbHMgYXJlIEFMV0FZUyB3aWRlciB0aGFuIGNvbmZpZGVuY2UgaW50ZXJ2YWxzLiANCg0KVGhlICQxMDBcYmV0YVwlJCBjb25maWRlbmNlIGludGVydmFsIGZvciAkeSA9IFxiZXRhXzAgKyBcYmV0YV8xIHggKyBlJCBpcyBnaXZlbiBieToNCg0KJCRcaGF0IHkgXHBtIHRfeyhuLTIsIFxhbHBoYSAvIDIpfSBcY2RvdCBzIFxzcXJ0ezEgKyBcZnJhY3sxfXtufSArIFxmcmFjeyh4IC0gXGJhciB4KV4yfXsobi0xKXNfWF4yfX0gJCQNClRoZSAkXGFscGhhJCBpbiB0aGUgZm9ybXVsYSBhYm92ZSBpcyBnaXZlbiBieSAkXGFscGhhID0gMSAtIFxiZXRhJC4gDQoNCg0KIyBTdW1tYXJ5IG9mIEZvcm11bGFzDQoNClRoZSAkMTAwXGJldGFcJSQgY29uZmlkZW5jZSBpbnRlcnZhbCBmb3IgJFxtYXRocm17RX1bWSB8IFg9eF0gPSBcYmV0YV8wICsgXGJldGFfMSB4JCBpcyBnaXZlbiBieToNCg0KJCRcaGF0IHkgXHBtIHRfeyhuLTIsIFxhbHBoYSAvIDIpfSBcY2RvdCBzIFxzcXJ0e1xmcmFjezF9e259ICsgXGZyYWN7KHggLSBcYmFyIHgpXjJ9eyhuLTEpc19YXjJ9fSAkJA0KVGhlICQxMDBcYmV0YVwlJCBjb25maWRlbmNlIGludGVydmFsIGZvciAkeSA9IFxiZXRhXzAgKyBcYmV0YV8xIHggKyBlJCBpcyBnaXZlbiBieToNCg0KJCRcaGF0IHkgXHBtIHRfeyhuLTIsIFxhbHBoYSAvIDIpfSBcY2RvdCBzIFxzcXJ0ezEgKyBcZnJhY3sxfXtufSArIFxmcmFjeyh4IC0gXGJhciB4KV4yfXsobi0xKXNfWF4yfX0gJCQNCkluIGVhY2ggZm9ybXVsYSwgd2UgaGF2ZSB0aGF0ICRcYWxwaGEgPSAxIC0gXGJldGEkLiANCg0KDQoNCiMgU2ltdWxhdGVkIEV4YW1wbGUNCg0KDQpgYGB7cn0NCnNldC5zZWVkKDEpDQpuID0gMTANCnggPC0gOCArIDE6biAvIDUNCnkgPC0gMip4ICsgMyArIHJub3JtKG4sMCwwLjgpDQoNCm1vZGVsIDwtIGxtKHl+eCkNCiAgICAgICAgICANCnBsb3QoeSB+IHgsIHhsaW09Yyg4LDEwLjEpLCB5bGltPWMoMTcsMjYpLCBjb2w9ImJsYWNrIiwgYmc9InJlZCIsIHBjaD0yMSwgY2V4PTEpDQphYmxpbmUobW9kZWwkY29lZmZpY2llbnRzLCBjb2w9ImJsdWUiLCBsd2Q9IjIiKQ0KDQoNCmBgYA0KDQpMZXQgZmluZCB0aGUgOTUlIGNvbmZpZGVuY2UgYW5kIHByZWRpY3Rpb24gaW50ZXJ2YWxzIGZvciAkWD05JC4gDQoNCmBgYHtyfQ0KbiA9IDEwDQp4XyA9IDkNCg0KeWhhdCA9IG1vZGVsJGNvZWZmaWNpZW50c1sxXSArIG1vZGVsJGNvZWZmaWNpZW50c1syXSAqIHhfDQoNCnMyID0gc3VtKChtb2RlbCRyZXNpZHVhbHMpXjIpIC8gKG4gLSAyKQ0KcyA9IHNxcnQoczIpDQoNCmNpX3NxcnQgPSBzcXJ0KDEvbiArICh4XyAtIG1lYW4oeCkpXjIgLyAoKG4tMSkgKiB2YXIoeCkpICkNCnBpX3NxcnQgPSBzcXJ0KDEgKyAxL24gKyAoeF8gLSBtZWFuKHgpKV4yIC8gKChuLTEpICogdmFyKHgpKSApDQoNCnQgPSBxdCgwLjk3NSwgbi0yKQ0KDQpjaSA9IGMoeWhhdCAtIHQgKiBzICogY2lfc3FydCwgeWhhdCArIHQgKiBzICogY2lfc3FydCkNCnBpID0gYyh5aGF0IC0gdCAqIHMgKiBwaV9zcXJ0LCB5aGF0ICsgdCAqIHMgKiBwaV9zcXJ0KQ0KDQpuYW1lcyhjaSkgPSBjKCdsb3dlcicsICd1cHBlcicpDQpuYW1lcyhwaSkgPSBjKCdsb3dlcicsICd1cHBlcicpDQoNCnJiaW5kKGNpLCBwaSkNCmBgYA0KDQpMZXQncyBjaGVjayBvdXIgYW5zd2VyIHVzaW5nIHRoZSBgcHJlZGljdCgpYCBmdW5jdGlvbi4NCg0KYGBge3J9DQpuZCA8LSBkYXRhLmZyYW1lKHg9OSkNCmNvbmYgPC0gcHJlZGljdChtb2RlbCwgaW50ZXJ2YWw9ImNvbmZpZGVuY2UiLCBsZXZlbD0wLjk1LCBuZXdkYXRhPW5kKQ0KcHJlZCA8LSBwcmVkaWN0KG1vZGVsLCBpbnRlcnZhbD0icHJlZGljdGlvbiIsIGxldmVsPTAuOTUsIG5ld2RhdGE9bmQpDQoNCnJiaW5kKGNvbmYsIHByZWQpDQpgYGANCg0KDQpgYGB7ciwgZWNobz1GQUxTRX0NCg0Kc2V0LnNlZWQoMSkNCnggPC0gOCArIDE6MTAgLyA1DQp5IDwtIDIqeCArIDMgKyBybm9ybSgxMCwwLDAuOCkNCg0KbW9kZWwgPC0gbG0oeX54KQ0KICAgICAgICAgIA0KbmQgPC0gZGF0YS5mcmFtZSh4PXNlcSg4LDEyLGxlbmd0aD01MSkpDQpwX2NvbmYgPC0gcHJlZGljdChtb2RlbCwgaW50ZXJ2YWw9ImNvbmZpZGVuY2UiLCBsZXZlbD0wLjk1LCBuZXdkYXRhPW5kKQ0KcF9wcmVkIDwtIHByZWRpY3QobW9kZWwsIGludGVydmFsPSJwcmVkaWN0aW9uIiwgbGV2ZWw9MC45NSwgbmV3ZGF0YT1uZCkNCiAgICAgICAgICANCnBsb3QoeSB+IHgsIHhsaW09Yyg4LDEwLjEpLCB5bGltPWMoMTcsMjYpLCBjb2w9ImJsYWNrIiwgYmc9InJlZCIsIHBjaD0yMSwgY2V4PTEpDQogICAgICAgICAgDQojIFRoZW9yZXRpY2FsIG1vZGVsDQojYWJsaW5lKDMsMiwgY29sPSJvcmFuZ2VyZWQiLCBsdHk9NSwgbHdkPTIpDQoNCiMgRml0dGVkIG1vZGVsDQphYmxpbmUobW9kZWwkY29lZmZpY2llbnRzLCBjb2w9ImJsdWUiLCBsd2Q9IjIiKQ0KIA0KIyBDb25maWRlbmNlIEJhbmQNCm1hdGxpbmVzKG5kJHgscF9jb25mWyxjKCJsd3IiLCJ1cHIiKV0sY29sPSJzbGF0ZWJsdWUxIiwgbHR5PTEsIGx3ZD0yLCB0eXBlPSJsIixwY2g9Ii4iKQ0KDQojIFByZWRpY3Rpb24gQmFuZA0KbWF0bGluZXMobmQkeCxwX3ByZWRbLGMoImx3ciIsInVwciIpXSxjb2w9Im1lZGl1bW9yY2hpZDEiLCBsdHk9MSwgbHdkPTIsIHR5cGU9ImwiLHBjaD0iLiIpDQpgYGANCg0KDQojIEV4YW1wbGUgVXNpbmcgUGVhcnNvbiBEYXRhDQoNCg0KV2Ugd2lsbCBub3cgd2FsayB0aHJvdWdoIGFuIGFub3RoZXIgZXhhbXBsZSBvZiB1c2luZyBSIHRvIGNyZWF0ZSBwcmVkaWN0aW9uIGFuZCBjb25maWRlbmNlIGludGVydmFscy4gSW4gdGhpcyBleGFtcGxlLCB3ZSB3aWxsIG9uY2UgYWdhaW4gdXNlIHRoZSBQZWFyc29uIGRhdGEgc2V0LiANCg0KV2Ugc3RhcnQgYnkgbG9hZGluZyB0aGUgZGF0YSBhbmQgY3JlYXRpbmcgb3VyIG1vZGVsLiANCg0KYGBge3J9DQpteURhdGEgPC0gcmVhZC50YWJsZSgiZmF0aGVyX3Nvbi50eHQiLCBzZXA9Ilx0IiwgaGVhZGVyPVRSVUUpDQoNCm1vZCA8LSBsbShzaGVpZ2h0IH4gZmhlaWdodCwgbXlEYXRhKQ0Kc3VtbWFyeShtb2QpDQpgYGANCg0KV2UgZ2VuZXJhdGUgYSBzY2F0dGVyIHBsb3Qgb2YgdGhlIGRhdGEsIHdpdGggdGhlIHJlZ3Jlc3Npb24gbGluZSBpbmNsdWRlZC4gDQoNCmBgYHtyfQ0KcGxvdChteURhdGEkc2hlaWdodCB+IG15RGF0YSRmaGVpZ2h0LCBwY2g9MjEsIGJnPSJjeWFuIiwgY29sPSJibGFjayIsIGNleD0xLA0KICAgICBtYWluPSJTY2F0dGVyIFBsb3QiLCB4bGFiPSJGYXRoZXIgSGVpZ2h0IiwgeWxhYj0iU29uIEhlaWdodCIpDQphYmxpbmUobW9kJGNvZWZmaWNpZW50cywgY29sPSJkYXJrcmVkIiwgbHdkPTIpDQpgYGANCg0KVGhlIGZvbGxvd2luZyBjb2RlIHVzZXMgb3VyIG1vZGVsIHRvIHByZWRpY3QgdGhlIGhlaWdodCBvZiBhbiBhZHVsdCBtYWxlIHdob3NlIGZhdGhlciBpcyA1IGZlZXQgdGFsbC4gDQoNCmBgYHtyfQ0KbmQxID0gZGF0YS5mcmFtZShmaGVpZ2h0PTYwKQ0KcHJlZGljdChtb2QsIG5ld2RhdGEgPSBuZCkNCmBgYA0KDQpMZXQncyBjcmVhdGUgYSA5NSUgY29uZmlkZW5jZSBpbnRlcnZhbCBmb3IgdGhlIGhlaWdodCBvZiBhbiBhZHVsdCBtYWxlIHdob3NlIGZhdGhlciBpcyA1IGZlZXQgdGFsbC4gUmVjYWxsIHRoYXQgdGhpcyBpbnRlcnZhbCBoYXMgYSA5NSUgY2hhbmNlIG9mIGluY2x1ZGluZyB0aGUgdHJ1ZSBwb3B1bGF0aW9uIG1lYW4gaGVpZ2h0IGZvciBzdWNoIGluZGl2aWR1YWxzLiBJdCBkb2VzIE5PVCBjbGFpbSB0byBjb250YWluIHRoZSBoZWlnaHRzIG9mIDk1JSBvZiB0aGVzZSBpbmRpdmlkdWFscy4gDQoNCmBgYHtyfQ0KcHJlZGljdChtb2QsIG5ld2RhdGEgPSBuZDEsIGludGVydmFsPSJjb25maWRlbmNlIiwgbGV2ZWw9Ljk1KQ0KYGBgDQoNCklmIHdlIHdhbnQgYW4gaW50ZXJ2YWwgdGhhdCB3ZSBiZWxpZXZlIHdpbGwgY29udGFpbiB0aGUgaGVpZ2h0cyBvZiA5NSUgb2YgYWxsIGFkdWx0IG1hbGVzIHdob3NlIGZhdGhlcnMgYXJlIDUgZmVldCB0YWxsLCB3ZSBuZWVkIHRvIGNvbnNpZGVyIGEgcHJlZGljdGlvbiBpbnRlcnZhbCBpbnN0ZWFkLiANCg0KYGBge3J9DQpwcmVkaWN0KG1vZCwgbmV3ZGF0YSA9IG5kMSwgaW50ZXJ2YWw9InByZWRpY3QiLCBsZXZlbD0uOTUpDQpgYGANCg0KTGV0J3MgZ2VuZXJhdGUgYSBwcmVkaWN0aW9uIGludGVydmFsIGZvciB0aGUgaGVpZ2h0IG9mIGFuIGFkdWx0IG1hbGUgd2hvc2UgZmF0aGVyIGlzIDYgZmVldCB0YWxsLiANCg0KYGBge3J9DQpuZDIgPSBkYXRhLmZyYW1lKGZoZWlnaHQ9NzIpDQpwcmVkaWN0KG1vZCwgbmV3ZGF0YSA9IG5kMiwgaW50ZXJ2YWw9InByZWRpY3QiLCBsZXZlbD0uOTUpDQpgYGANCg0KV2UgY2FuIGFsc28gdXNlIGBwcmVkaWN0KClgIHRvIGNyZWF0ZSBwcmVkaWN0aW9ucyBmb3Igc2V2ZXJhbCB2YWx1ZXMgb2YgdGhlIHByZWRpY3RvciBhdCBvbmNlLiANCg0KYGBge3J9DQpuZDMgPSBkYXRhLmZyYW1lKGZoZWlnaHQ9Yyg2MCwgNjIsIDY0LCA2NiwgNjgsIDcwLCA3MikpDQpwcmVkaWN0KG1vZCwgbmV3ZGF0YSA9IG5kMywgaW50ZXJ2YWw9InByZWRpY3QiLCBsZXZlbD0uOTUpDQpgYGANCg0KDQpgYGB7ciwgZWNobz1GQUxTRX0NCiNmaGVpZ2h0ID0gbXlEYXRhJGZoZWlnaHQNCg0KbmQ0IDwtIGRhdGEuZnJhbWUoZmhlaWdodD1zZXEoNTUsODAsbGVuZ3RoPTUxKSkNCnBfY29uZiA8LSBwcmVkaWN0KG1vZCwgaW50ZXJ2YWw9ImNvbmZpZGVuY2UiLCBsZXZlbD0wLjk1LCBuZXdkYXRhID0gbmQ0KQ0KcF9wcmVkIDwtIHByZWRpY3QobW9kLCBpbnRlcnZhbD0icHJlZGljdGlvbiIsIGxldmVsPTAuOTUsIG5ld2RhdGEgPSBuZDQpDQogICAgICAgICAgDQpwbG90KG15RGF0YSRzaGVpZ2h0IH4gbXlEYXRhJGZoZWlnaHQsIHBjaD0yMSwgYmc9ImN5YW4iLCBjb2w9ImJsYWNrIiwgY2V4PTEsDQogICAgIG1haW49IlNjYXR0ZXIgUGxvdCIsIHhsYWI9IkZhdGhlciBIZWlnaHQiLCB5bGFiPSJTb24gSGVpZ2h0IikNCg0KYWJsaW5lKG1vZCRjb2VmZmljaWVudHMsIGNvbD0iZGFya3JlZCIsIGx3ZD0yKQ0KDQojIENvbmZpZGVuY2UgQmFuZA0KbWF0bGluZXMobmQ0JGZoZWlnaHQsIHBfY29uZlssYygibHdyIiwidXByIildLGNvbD0iZGFya29yY2hpZCIsIGx0eT0xLCBsd2Q9MiwgdHlwZT0ibCIscGNoPSIuIikNCg0KIyBQcmVkaWN0aW9uIEJhbmQNCm1hdGxpbmVzKG5kNCRmaGVpZ2h0LCBwX3ByZWRbLGMoImx3ciIsInVwciIpXSxjb2w9ImRhcmtvcmNoaWQxIiwgbHR5PTEsIGx3ZD0yLCB0eXBlPSJsIixwY2g9Ii4iKQ0KYGBgDQoNCg0KDQoNCg0KDQo=