library(zoo)
library(tseries)
library(lmtest)
library(sandwich)
library(car)
rm(list=ls())

Pokračujeme v predchádzajúcich úlohách, kde s pomocou regresnej analýzy skúmame, ako demografické ukazovatele ovplyvňujú predpokladanú veľkosť populácie krajín v roku 2025. V našom modeli sa zameriavame na tri hlavné vysvetľujúce premenné:

Cieľom analýzy je zistiť, či a akým spôsobom tieto demografické faktory prispievajú k očakávanému počtu obyvateľov v roku 2025.
Výsledok regresie je uvedený nižšie.

############################################################
# PRÍPRAVA ÚDAJOV
############################################################

# načítanie dát
údaje <- read.csv("population_data.csv",
                  sep = ",",
                  dec = ".",
                  header = TRUE)

údaje$Fert..Rate <- as.numeric(as.character(údaje$Fert..Rate))
údaje$Median.Age <- as.numeric(as.character(údaje$Median.Age))
údaje$Migrants..net. <- as.numeric(as.character(údaje$Migrants..net.))
údaje$Population.2025 <- as.numeric(as.character(údaje$Population.2025))

data_selected <- údaje[, c("Population.2025", "Fert..Rate", "Median.Age", "Migrants..net.")]

# výber premenných, s ktorými pracujeme
data_selected <- údaje[, c("Population.2025",
                           "Fert..Rate",
                           "Median.Age",
                           "Migrants..net.")]

# odstránenie chýbajúcich hodnôt imputáciou mediánom
column_medians <- sapply(data_selected, median, na.rm = TRUE)

data_imputed <- data_selected
for (col in names(data_imputed)) {
  data_imputed[[col]][is.na(data_imputed[[col]])] <- column_medians[col]
}

# konečný dataset
data_selected <- data_imputed


################################################################################
# ZAKLADNA REGRESIA
################################################################################
attach(údaje)
model <- lm(Population.2025 ~ Fert..Rate + Median.Age + Migrants..net., 
            data = data_selected)
summary(model)

Call:
lm(formula = Population.2025 ~ Fert..Rate + Median.Age + Migrants..net., 
    data = data_selected)

Residuals:
       Min         1Q     Median         3Q        Max 
-140219782  -35078796  -24786817   -5778921 1417079953 

Coefficients:
                 Estimate Std. Error t value Pr(>|t|)
(Intercept)     1.457e+08  8.995e+07   1.620    0.107
Fert..Rate     -1.893e+07  1.553e+07  -1.219    0.224
Median.Age     -2.177e+06  1.784e+06  -1.221    0.224
Migrants..net.  8.427e+01  6.307e+01   1.336    0.183

Residual standard error: 1.39e+08 on 229 degrees of freedom
Multiple R-squared:  0.01507,   Adjusted R-squared:  0.002167 
F-statistic: 1.168 on 3 and 229 DF,  p-value: 0.3227

Testovať, či je model v správnej funkčnej forme (t. j. či je lineárna špecifikácia vhodná, alebo či by ste mali transformovať premenné, napríklad pomocou logaritmov alebo mocninami), možno vykonať viacerými spôsobmi.

1. Test RESET (test chyby špecifikácie Ramseyho regresnej rovnice - Ramsey Reset Test)

Ide o najštandardnejší formálny test nesprávnej špecifikácie funkčnej formy ale dá sa použiť aj pre prípady, ak sme nešpecifikovali všetky vysvetľujúce premenné.

Myšlienka: Nech pôvodný model má tvar \[y_t = \beta_0 + \beta_1 x_{t10} + \dots +\beta_k x_{tk} + u_t\] Ak je váš model správne špecifikovaný, potom pridaním mocnín vyrovnaných hodnôt (napr. \(\hat y_t^2\), \(\hat{y}_t^3\)) by sa pôvodný model nemal podstatne zlepšiť, teda budeme testovať pôvodný model uvedený vyššie a model

\[y_t = \beta_0 + \beta_1 x_{t10} + \dots +\beta_k x_{tk} + \gamma_2\hat y_t^2 + \gamma_3\hat{y}_t^3 + u_t\]

Budeme testovať hypotézu

\(H_0:\) model je správne špecifikovaný (\(\gamma_2 = \gamma_3 = 0\))

oproti

\(H_1:\) model je nesprávne špecifikovaný (\(\gamma_2 \ne 0 \quad \text{alebo} \quad \gamma_3 \ne 0\))

library(lmtest)

# tvoj model:
model <- lm(Population.2025 ~ Fert..Rate + Median.Age + Migrants..net., 
            data = data_selected)

# RESET test – test nesprávnej špecifikácie modelu
reset_results <- resettest(model, power = 2:3, type = "fitted")
reset_results

    RESET test

data:  model
RESET = 0.9428, df1 = 2, df2 = 227, p-value = 0.3911

Interpretácia: 🧪 RESET test – kontrola špecifikácie modelu

Výsledok RESET testu:

Keďže p-value je vyššia ako 0.05, nezamietame nulovú hypotézu, že model je správne špecifikovaný.

➡️ Model nepreukazuje chybnú funkčnú formu.
➡️ Nie je potrebné pridávať nelineárne členy ani ďalšie premenné.

Model podľa RESET testu zodpovedá vhodnej špecifikácii.

2. Grafická analýza

Graf Residuals vs. Fitted

Grafická analýza vzťahu medzi vyrovnanými hodnotami náhodnej premennej a rezíduami:

plot(model, which = 1)

📊 Interpretácia grafu Residuals vs. Fitted

Na grafe Residuals vs. Fitted si všímame rozloženie reziduí okolo horizontálnej čiary.
Z nášho grafu možno pozorovať nasledovné:

✅ Záver

Na základe grafickej diagnostiky možno povedať, že model nevykazuje závažné štrukturálne problémy.
Správanie reziduí je primerane náhodné, čo podporuje závery aj z RESET testu.

Grafy C+R **

Táto analýza nám môže pomôcť pri hľadaní odpovede na otázku, ktorú premennú by sme mali transfomovať pomocou nejakej známej funkcie. Vychádzajme z pôvodnej rovnice

\[y_t = \beta_0 + \beta_1 x_{t1} + \dots +\beta_k x_{tk} + u_t\] Túto rovnicu najprv odhadneme a potom vykresľujeme grafy, kde výraz component+residual (C+R) plot vykresľuje na zvislej osi \(\hat{\beta}_ix_{ti}+e_t\) a na vodorovnej osi vykresľuje hodnoty \(x_{ti}\)

Tieto grafy pomáhajú identifikovať nelineárne vzťahy pre každý regresor:

car::crPlots(model)

📊 Interpretácia Component + Residual (C+R) grafov

Cieľom C+R grafov je overiť, či je vzťah medzi jednotlivými regresormi a závislou premennou lineárny, alebo či by mohla byť vhodná transformácia (logaritmus, mocnina a pod.).
Nižšie uvádzam interpretáciu pre každý regresor.


1️⃣ Premenná Fert..Rate

➡️ Lineárny tvar je postačujúci, transformácia nie je potrebná.


2️⃣ Premenná Median.Age

➡️ Lineárna špecifikácia je vhodná, transformácia nie je potrebná.


3️⃣ Premenná Migrants..net.

➡️ Možná kandidátka na transformáciu (napr. logaritmus), ale odklon nie je dramatický a model funguje aj bez úprav.


Zhrnutie

C+R grafy naznačujú, že regresory Fert..Rate a Median.Age majú lineárny vzťah so závislou premennou. Premenná Migrants..net. ukazuje mierne nelineárny trend, ale nie natoľko výrazný, aby bolo nevyhnutné meniť špecifikáciu modelu. Celkovo grafy nepoukazujú na potrebu zásadných transformácií premenných.

3. Nelineárna špecifikácia

Častokrát môžeme aj zložitejšie nelineárne vzťahy modelovať s pomocou ich aproximácie s polynómom, teda v prípade kvadratických členov

\[y_t = \beta_0 + \beta_1 x_{t10} + \dots +\beta_k x_{tk} + \dots + \gamma_i\hat x_{ik}^2 + \dots + \gamma_j\hat x_{jk}^2 + \dots + u_t\] Príklad na túto modifikáciu uvidíme nižšie.

4. Porovnanie základného a modifikovaného modelu

Na základe grafov Component + Residual sme identifikovali, že najväčší odklon od linearity vykazujú premenné Median.Age a Migrants..net.. Tieto premenné nevytvárajú striktne lineárny vzťah so závislou premennou Population.2025, čo naznačuje možnú potrebu doplnenia kvadratických členov.

Preto predpokladáme, že pri nelineárnych úpravách pôvodného modelu dôjde k zlepšeniu jeho špecifikácie práve po zavedení kvadrátov premenných Median.Age² a Migrants..net.². Ich správanie v C+R grafoch naznačovalo mierne zakrivenie, ktoré sa výraznejšie odchyľovalo od priamky.

Ak má transformovaný model vyšší upravený koeficient determinácie \(R^2_{adj}\), lepšiu štatistickú významnosť a zároveň RESET test nepotvrdí nesprávnu špecifikáciu, môžeme nový model považovať za vhodnejší. Odporúčame výsledky ďalej podporiť aj porovnaním oboch modelov pomocou ANOVA testu, ktorý overí, či má rozšírený model štatisticky významne lepšiu výkonnosť.

# Základný lineárny model
model <- lm(Population.2025 ~ 1 + Fert..Rate + Median.Age + Migrants..net., 
            data = data_selected)

# Model s kvadratickými členmi na základe C+R grafov
model_kvadr <- lm(Population.2025 ~ 1 + Fert..Rate + 
                    Median.Age + I(Median.Age^2) +
                    Migrants..net. + I(Migrants..net.^2),
                  data = data_selected)

# Výstupy modelu
summary(model_kvadr)

Call:
lm(formula = Population.2025 ~ 1 + Fert..Rate + Median.Age + 
    I(Median.Age^2) + Migrants..net. + I(Migrants..net.^2), data = data_selected)

Residuals:
       Min         1Q     Median         3Q        Max 
 -93614219  -33867568  -24064751   -8026469 1418718877 

Coefficients:
                      Estimate Std. Error t value Pr(>|t|)
(Intercept)          1.873e+08  2.533e+08   0.739    0.461
Fert..Rate          -2.194e+07  2.375e+07  -0.923    0.357
Median.Age          -4.326e+06  1.151e+07  -0.376    0.707
I(Median.Age^2)      2.863e+04  1.502e+05   0.191    0.849
Migrants..net.       2.049e+02  1.952e+02   1.050    0.295
I(Migrants..net.^2) -8.655e-05  1.324e-04  -0.654    0.514

Residual standard error: 139500000 on 227 degrees of freedom
Multiple R-squared:  0.01705,   Adjusted R-squared:  -0.004599 
F-statistic: 0.7876 on 5 and 227 DF,  p-value: 0.5596
# Porovnanie základného a nelineárneho modelu
anova(model, model_kvadr)
Analysis of Variance Table

Model 1: Population.2025 ~ 1 + Fert..Rate + Median.Age + Migrants..net.
Model 2: Population.2025 ~ 1 + Fert..Rate + Median.Age + I(Median.Age^2) + 
    Migrants..net. + I(Migrants..net.^2)
  Res.Df        RSS Df  Sum of Sq      F Pr(>F)
1    229 4.4270e+18                            
2    227 4.4181e+18  2 8.9087e+15 0.2289 0.7956
# RESET test pre nelineárne rozšírený model
resettest(model_kvadr)

    RESET test

data:  model_kvadr
RESET = 0.74875, df1 = 2, df2 = 225, p-value = 0.4741

Takto modifikovaný model, v ktorom sme doplnili kvadrát premenných Median.Age a Migrants..net., však neoznačuje žiadny z kvadratických členov za štatisticky významný (p-hodnoty sú výrazne väčšie ako 0,05). Zároveň nedochádza k zlepšeniu upraveného koeficientu determinácie – naopak, jeho hodnota klesla na približne \(R^2_{\text{adj}} \approx -0{.}0046\).

Aj porovnanie modelov pomocou ANOVA (p-hodnota \(\approx 0{.}80\)) a RESET testu (p-hodnota \(\approx 0{.}47\)) ukazuje, že kvadratický model nie je lepší než pôvodný lineárny model. V ďalšej analýze preto pracujeme s jednoduchším lineárnym modelom bez kvadratických členov.

model_kvadr <- lm(Population.2025 ~ 1 + Fert..Rate + Median.Age + Migrants..net. +
                    I(Median.Age^2) + I(Migrants..net.^2),
                  data = data_selected)

summary(model_kvadr)

Call:
lm(formula = Population.2025 ~ 1 + Fert..Rate + Median.Age + 
    Migrants..net. + I(Median.Age^2) + I(Migrants..net.^2), data = data_selected)

Residuals:
       Min         1Q     Median         3Q        Max 
 -93614219  -33867568  -24064751   -8026469 1418718877 

Coefficients:
                      Estimate Std. Error t value Pr(>|t|)
(Intercept)          1.873e+08  2.533e+08   0.739    0.461
Fert..Rate          -2.194e+07  2.375e+07  -0.923    0.357
Median.Age          -4.326e+06  1.151e+07  -0.376    0.707
Migrants..net.       2.049e+02  1.952e+02   1.050    0.295
I(Median.Age^2)      2.863e+04  1.502e+05   0.191    0.849
I(Migrants..net.^2) -8.655e-05  1.324e-04  -0.654    0.514

Residual standard error: 139500000 on 227 degrees of freedom
Multiple R-squared:  0.01705,   Adjusted R-squared:  -0.004599 
F-statistic: 0.7876 on 5 and 227 DF,  p-value: 0.5596

Porovnanie základného a kvadraticky modifikovaného modelu

Do modelu sme pridali kvadratické členy premenných Median.Age a Migrants..net. s cieľom zachytiť možné nelineárne vzťahy. Výsledky však ukazujú, že ani jeden z týchto kvadratických členov nie je štatisticky významný (všetky p-hodnoty sú výrazne väčšie ako 0.05).

Upravený koeficient determinácie zostal v podstate nezmenený a má hodnotu
\(R^2_{adj} = -0.0046\), čo naznačuje, že kvadraticky rozšírený model nevysvetľuje variabilitu dát lepšie ako pôvodný model.

Zavedenie kvadratických členov preto neprinieslo zlepšenie a v ďalšej analýze budeme pokračovať s pôvodným lineárnym modelom.

5. Použitie rozšíreného RESET testu

model_rozsireny <- lm(
  Population.2025 ~ 
    Fert..Rate +
    Median.Age +
    Migrants..net. +
    I(Median.Age^2) +
    I(Migrants..net.^2),
  data = data_selected
)

summary(model_rozsireny)

Call:
lm(formula = Population.2025 ~ Fert..Rate + Median.Age + Migrants..net. + 
    I(Median.Age^2) + I(Migrants..net.^2), data = data_selected)

Residuals:
       Min         1Q     Median         3Q        Max 
 -93614219  -33867568  -24064751   -8026469 1418718877 

Coefficients:
                      Estimate Std. Error t value Pr(>|t|)
(Intercept)          1.873e+08  2.533e+08   0.739    0.461
Fert..Rate          -2.194e+07  2.375e+07  -0.923    0.357
Median.Age          -4.326e+06  1.151e+07  -0.376    0.707
Migrants..net.       2.049e+02  1.952e+02   1.050    0.295
I(Median.Age^2)      2.863e+04  1.502e+05   0.191    0.849
I(Migrants..net.^2) -8.655e-05  1.324e-04  -0.654    0.514

Residual standard error: 139500000 on 227 degrees of freedom
Multiple R-squared:  0.01705,   Adjusted R-squared:  -0.004599 
F-statistic: 0.7876 on 5 and 227 DF,  p-value: 0.5596

V tomto kroku testujeme, či kvadratické členy Median.Age² a Migrants..net.²
prinášajú do modelu štatisticky významné informácie.
Ak by boli významné, mali by sme uvažovať nad kvadratickou transformáciou týchto premenných.

Na základe výstupu summary(model_rozsireny) však vidíme, že:

  • koeficient pri I(Median.Age^2) nie je štatisticky významný (p = 0.849),
  • koeficient pri I(Migrants..net.^2) taktiež nie je štatisticky významný (p = 0.514).
anova(model,model_rozsireny)
Analysis of Variance Table

Model 1: Population.2025 ~ 1 + Fert..Rate + Median.Age + Migrants..net.
Model 2: Population.2025 ~ Fert..Rate + Median.Age + Migrants..net. + 
    I(Median.Age^2) + I(Migrants..net.^2)
  Res.Df        RSS Df  Sum of Sq      F Pr(>F)
1    229 4.4270e+18                            
2    227 4.4181e+18  2 8.9087e+15 0.2289 0.7956
resettest(model_rozsireny)

    RESET test

data:  model_rozsireny
RESET = 0.74875, df1 = 2, df2 = 225, p-value = 0.4741

Pri RESET teste vidíme, že p-hodnota 0.4741 je výrazne vyššia ako hladina významnosti 0.05.
To znamená, že nezamietame nulovú hypotézu správnej špecifikácie modelu.

Zároveň však platí, že ani rozšírený model s kvadratickými členmi nebol štatisticky významný
(ANOVA p = 0.7956), takže prípadný problém nesprávnej špecifikácie modelu sa neodstránil,
ale zároveň nebol ani potvrdený. Zavedenie kvadratických členov neprinieslo zlepšenie modelu.

6. Transformácia pomocou dummy premennej a lineárnej lomenej funkcie

Predpokladajme, že máme dummy premennú \(D_t\), ktorá obsahuje len nuly a jedničky. Takáto premenná sa dá využiť modelovanie zlomov, a to napr.

  1. zlom v autonómnom člene \(\beta_0\) a to nasledovnou špecifikáciou \[y_t = \beta_0 + \beta_D D+ \beta_1 x_{t1} + \dots +\beta_k x_{tk} + u_t\] čo interpretujeme ako posun regresnej priamky (regresnej nadroviny) o \(\beta_D\) jednotiek pozdĺž zvislej osi a to len v pozorovaniach, ak je splnená podmienka \(D_t = 1\)
  2. zlom v sklone regresnej priamky (nadroviny) a to len v pozorovaniach, ak je splnená podmienka \(D_t = 1\), čo dosiahneme nasledovnou špecifikáciou \[y_t = \beta_0 + \beta_1 x_{t1} + \dots + \beta_{i}x_{ti} + \beta_{Di}D_tx_{ti}+ \dots + \beta_k x_{tk} + u_t\] kde teda sklon priamky pozdĺž premenne \(x_{ti}\) je \(\beta_i\) ale len v prípade \(D_t=0\), inak je ten sklon rovný \(\beta_i+\beta_{D_i}\).

Ak si pozrieme C+R grafy pre naše vysvetľujúce premenné, vidíme, že najvýraznejšie odchýlky od linearity sa objavujú pri premenných Migrants..net. a Median.Age. Vyrovnaná krivka pri oboch premenných naznačuje mierne zakrivenie, najmä pri extrémnejších hodnotách, čo môže signalizovať potrebu nelineárnej úpravy (t.j. zavedenie kvadratického člena). Preto sme do modelu zaradili premenné I(Median.Age²) a I(Migrants..net.²), aby sme otestovali, či tieto nelineárne efekty dokážu zlepšiť špecifikáciu modelu.

Kvantifikujme teraz model so zlomom v autonómnom členovi.
Keďže podľa C+R grafov zaznamenávame nelineárne správanie pri premenných Migrants..net., zavedieme novú dummy premennú, ktorá rozdelí krajiny podľa úrovne migrácie.

Nech
\(DUM_t = 0\) pre hodnoty Migrants..net. nižšie ako medián
a
\(DUM_t = 1\) pre hodnoty Migrants..net. vyššie alebo rovné mediánu.

Takto budeme môcť posúdiť, či sa intercept modelu výrazne mení pri vyšších hodnotách migrácie.

# prah si môžeme určiť ako medián
threshold <- median(data_selected$Migrants..net., na.rm = TRUE)

# dummy premenná podľa prahu
data_selected$DUM <- ifelse(data_selected$Migrants..net. < threshold, 0, 1)

# model so zlomom v autonómnom členovi
model_auto <- lm(Population.2025 ~ 1 + DUM + Fert..Rate + Median.Age +
                   Migrants..net., 
                 data = data_selected)

summary(model_auto)

Call:
lm(formula = Population.2025 ~ 1 + DUM + Fert..Rate + Median.Age + 
    Migrants..net., data = data_selected)

Residuals:
       Min         1Q     Median         3Q        Max 
-128357100  -38514919  -22145390    1662071 1409733516 

Coefficients:
                 Estimate Std. Error t value Pr(>|t|)  
(Intercept)     1.053e+08  9.279e+07   1.135   0.2577  
DUM             3.905e+07  2.333e+07   1.674   0.0955 .
Fert..Rate     -1.922e+07  1.547e+07  -1.243   0.2152  
Median.Age     -1.852e+06  1.787e+06  -1.036   0.3011  
Migrants..net.  7.029e+01  6.337e+01   1.109   0.2686  
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

Residual standard error: 138500000 on 228 degrees of freedom
Multiple R-squared:  0.02703,   Adjusted R-squared:  0.009957 
F-statistic: 1.583 on 4 and 228 DF,  p-value: 0.1796

Zavedením zlomovej premennej DUM došlo k miernemu zlepšeniu modelu, keďže koeficient pri DUM vyšiel na hladine významnosti 10 % štatisticky významný (p ≈ 0.0955). To naznačuje, že pre krajiny nad zvolenou hranicou fertility sa úroveň populácie systematicky líši (má iný intercept). Ostatné premenné ostali nevýznamné a upravený R² zostal veľmi nízky (≈ 0.00996). Celkový F-test naznačuje, že model ako celok nie je významný (p ≈ 0.1796). Zavedenie zlomovej premennej preto neprinieslo zásadné zlepšenie kvality modelu.

modelD_sklon <- lm(Population.2025 ~ 1 + Fert..Rate + I(DUM * Fert..Rate) +
                     Median.Age + Migrants..net., 
                   data = data_selected)

summary(modelD_sklon)

Call:
lm(formula = Population.2025 ~ 1 + Fert..Rate + I(DUM * Fert..Rate) + 
    Median.Age + Migrants..net., data = data_selected)

Residuals:
       Min         1Q     Median         3Q        Max 
-131583667  -36676438  -22886410    -753794 1411771077 

Coefficients:
                      Estimate Std. Error t value Pr(>|t|)  
(Intercept)          1.444e+08  8.974e+07   1.610   0.1089  
Fert..Rate          -3.348e+07  1.850e+07  -1.810   0.0717 .
I(DUM * Fert..Rate)  1.549e+07  1.077e+07   1.439   0.1517  
Median.Age          -2.011e+06  1.783e+06  -1.128   0.2606  
Migrants..net.       7.529e+01  6.323e+01   1.191   0.2350  
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

Residual standard error: 138700000 on 228 degrees of freedom
Multiple R-squared:  0.02393,   Adjusted R-squared:  0.006805 
F-statistic: 1.397 on 4 and 228 DF,  p-value: 0.2357

📌 Interpretácia výsledkov modelu so zlomom v sklone (interakcia DUM * Fert..Rate)

V tomto kroku sme do modelu zaviedli zmenu sklonu pre premennú Fert..Rate pomocou interakčného člena I(DUM * Fert..Rate). Premenná DUM rozdeľuje pozorovania na dve skupiny podľa vopred určenej hranice a testujeme, či fertilita ovplyvňuje veľkosť populácie rozdielne v týchto dvoch skupinách.


📊 Výsledky regresného modelu

  • Fert..Rate
    • odhad: -3.348e+07
    • p-hodnota: 0.0717
      → účinok je slabo významný (približne na 10 % hladine).
  • Interakcia DUM * Fert..Rate
    • odhad: 1.549e+07
    • p-hodnota: 0.1517
      → interakčný efekt nie je štatisticky významný, teda sklon Fert..Rate sa po zmene DUM výrazne nemení.
  • Median.Age
    • p-hodnota: 0.2606
      → nevýznamný efekt.
  • Migrants..net.
    • p-hodnota: 0.2350
      → takisto nevýznamný efekt.

📈 Hodnotenie kvality modelu

  • Multiple R-squared: 0.02393

  • Adjusted R-squared: 0.006805
    → model vysvetľuje len približne 2,4 % variability v údajoch.

  • F-test modelu: p-hodnota = 0.2357
    → model ako celok nie je štatisticky významný.


📝 Záver

  • Interakčný člen DUM * Fert..Rate nezlepšil kvalitu modelu a nie je štatisticky významný.
  • Neexistuje dôkaz, že fertilita má odlišný vplyv na populáciu v roku 2025 medzi dvomi skupinami definovanými podľa premennej DUM.
  • Model má veľmi nízke hodnoty \(R^2\) aj \(R^2_{\text{adj}}\), čo znamená slabú vysvetľovaciu schopnosť.
  • Model so zlomom v sklone preto neodporúčame používať ako finálny model.

anova(model, modelD_sklon)
Analysis of Variance Table

Model 1: Population.2025 ~ 1 + Fert..Rate + Median.Age + Migrants..net.
Model 2: Population.2025 ~ 1 + Fert..Rate + I(DUM * Fert..Rate) + Median.Age + 
    Migrants..net.
  Res.Df        RSS Df Sum of Sq      F Pr(>F)
1    229 4.4270e+18                           
2    228 4.3872e+18  1 3.982e+16 2.0694 0.1517
resettest(modelD_sklon)

    RESET test

data:  modelD_sklon
RESET = 0.92117, df1 = 2, df2 = 226, p-value = 0.3995

📌 Porovnanie modelov pomocou ANOVA a RESET testu

Na overenie, či zavedenie interakčného člena DUM * Fert..Rate viedlo k zlepšeniu špecifikácie modelu, sme použili ANOVA test a následne aj RESET test.


🔍 Výsledky ANOVA testu

ANOVA porovnáva:

  • Model 1:
    Population.2025 ~ 1 + Fert..Rate + Median.Age + Migrants..net.
  • Model 2 (rozšírený):
    Population.2025 ~ 1 + Fert..Rate + I(DUM * Fert..Rate) + Median.Age + Migrants..net.

Výsledok:

  • F = 2.0694,
  • p-hodnota = 0.1517

👉 Keďže p-hodnota je väčšia ako 0.05, rozšírený model nevykazuje štatisticky významné zlepšenie oproti základnému modelu.
Interakčný člen teda neprispel k lepšiemu vysvetleniu variability v dátach.


🧪 RESET test pre model so zlomom v sklone

Výsledok RESET testu:

  • RESET = 0.92117
  • df1 = 2, df2 = 226
  • p-hodnota = 0.3995

👉 Keďže p-hodnota je opäť oveľa vyššia ako 0.05, nezamietame nulovú hypotézu správnej špecifikácie modelu.
RESET test teda neindicuje chybnú funkčnú formu, ale zároveň ani nepotvrdzuje, že interakcia priniesla zlepšenie.


📝 Záver

  • Ani ANOVA, ani RESET test nepreukázali, že by zavedenie interakčného člena DUM * Fert..Rate prispelo k zlepšeniu modelu.
  • Model so zlomom v sklone nie je štatisticky lepší ako pôvodný model.
  • Neexistuje dôkaz, že fertilita má odlišný vplyv na populáciu v rôznych skupinách definovaných premennou DUM.
  • Zostávame teda pri závere, že tento model nie je vhodný ako finálny a nepodporuje hypotézu o zmene sklonu.

LS0tCnRpdGxlOiAiTmVsaW5lw6FybmUgxaFwZWNpZmlrw6FjaWUiCm91dHB1dDogaHRtbF9ub3RlYm9vawphdXRob3I6IFJhZG92YW4gU3RhbsSNw61rCi0tLQoKYGBge3Igc2V0dXAsIGluY2x1ZGU9RkFMU0V9CmtuaXRyOjpvcHRzX2NodW5rJHNldChlY2hvID0gVFJVRSkKYGBgCgpgYGB7cn0KbGlicmFyeSh6b28pCmxpYnJhcnkodHNlcmllcykKbGlicmFyeShsbXRlc3QpCmxpYnJhcnkoc2FuZHdpY2gpCmxpYnJhcnkoY2FyKQpybShsaXN0PWxzKCkpCmBgYAoKUG9rcmHEjXVqZW1lIHYgcHJlZGNow6FkemFqw7pjaWNoIMO6bG9ow6FjaCwga2RlIHMgcG9tb2NvdSByZWdyZXNuZWogYW5hbMO9enkgc2vDum1hbWUsIApha28gZGVtb2dyYWZpY2vDqSB1a2F6b3ZhdGVsZSBvdnBseXbFiHVqw7ogcHJlZHBva2xhZGFuw7ogdmXEvmtvc8WlIHBvcHVsw6FjaWUga3JhasOtbiB2IHJva3UgMjAyNS4gClYgbmHFoW9tIG1vZGVsaSBzYSB6YW1lcmlhdmFtZSBuYSB0cmkgaGxhdm7DqSB2eXN2ZXTEvnVqw7pjZSBwcmVtZW5uw6k6CgotICoqbWllcmEgcGxvZG5vc3RpIChGZXJ0aWxpdHkgUmF0ZSwgcG91xb5pdMOhIHYgbG9nYXJpdG1vdmFuZWogZm9ybWUpLCoqCi0gKiptZWRpw6Fub3bDvSB2ZWsgb2J5dmF0ZcS+c3R2YSAoTWVkaWFuIEFnZSksKioKLSAqKsSNaXN0w6EgbWlncsOhY2lhIChNaWdyYW50cy5uZXQpLioqCgpDaWXEvm9tIGFuYWzDvXp5IGplIHppc3RpxaUsIMSNaSBhIGFrw71tIHNww7Rzb2JvbSB0aWV0byBkZW1vZ3JhZmlja8OpIGZha3RvcnkgCnByaXNwaWV2YWrDuiBrIG/EjWFrw6F2YW7DqW11IHBvxI10dSBvYnl2YXRlxL5vdiB2IHJva3UgMjAyNS4gIApWw71zbGVkb2sgcmVncmVzaWUgamUgdXZlZGVuw70gbmnFvsWhaWUuCgpgYGB7cn0KIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjCiMgUFLDjVBSQVZBIMOaREFKT1YKIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjCgojIG5hxI3DrXRhbmllIGTDoXQKw7pkYWplIDwtIHJlYWQuY3N2KCJwb3B1bGF0aW9uX2RhdGEuY3N2IiwKICAgICAgICAgICAgICAgICAgc2VwID0gIiwiLAogICAgICAgICAgICAgICAgICBkZWMgPSAiLiIsCiAgICAgICAgICAgICAgICAgIGhlYWRlciA9IFRSVUUpCgrDumRhamUkRmVydC4uUmF0ZSA8LSBhcy5udW1lcmljKGFzLmNoYXJhY3RlcijDumRhamUkRmVydC4uUmF0ZSkpCsO6ZGFqZSRNZWRpYW4uQWdlIDwtIGFzLm51bWVyaWMoYXMuY2hhcmFjdGVyKMO6ZGFqZSRNZWRpYW4uQWdlKSkKw7pkYWplJE1pZ3JhbnRzLi5uZXQuIDwtIGFzLm51bWVyaWMoYXMuY2hhcmFjdGVyKMO6ZGFqZSRNaWdyYW50cy4ubmV0LikpCsO6ZGFqZSRQb3B1bGF0aW9uLjIwMjUgPC0gYXMubnVtZXJpYyhhcy5jaGFyYWN0ZXIow7pkYWplJFBvcHVsYXRpb24uMjAyNSkpCgpkYXRhX3NlbGVjdGVkIDwtIMO6ZGFqZVssIGMoIlBvcHVsYXRpb24uMjAyNSIsICJGZXJ0Li5SYXRlIiwgIk1lZGlhbi5BZ2UiLCAiTWlncmFudHMuLm5ldC4iKV0KCiMgdsO9YmVyIHByZW1lbm7DvWNoLCBzIGt0b3LDvW1pIHByYWN1amVtZQpkYXRhX3NlbGVjdGVkIDwtIMO6ZGFqZVssIGMoIlBvcHVsYXRpb24uMjAyNSIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICJGZXJ0Li5SYXRlIiwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIk1lZGlhbi5BZ2UiLAogICAgICAgICAgICAgICAgICAgICAgICAgICAiTWlncmFudHMuLm5ldC4iKV0KCiMgb2RzdHLDoW5lbmllIGNow71iYWrDumNpY2ggaG9kbsO0dCBpbXB1dMOhY2lvdSBtZWRpw6Fub20KY29sdW1uX21lZGlhbnMgPC0gc2FwcGx5KGRhdGFfc2VsZWN0ZWQsIG1lZGlhbiwgbmEucm0gPSBUUlVFKQoKZGF0YV9pbXB1dGVkIDwtIGRhdGFfc2VsZWN0ZWQKZm9yIChjb2wgaW4gbmFtZXMoZGF0YV9pbXB1dGVkKSkgewogIGRhdGFfaW1wdXRlZFtbY29sXV1baXMubmEoZGF0YV9pbXB1dGVkW1tjb2xdXSldIDwtIGNvbHVtbl9tZWRpYW5zW2NvbF0KfQoKIyBrb25lxI1uw70gZGF0YXNldApkYXRhX3NlbGVjdGVkIDwtIGRhdGFfaW1wdXRlZAoKCiMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjCiMgWkFLTEFETkEgUkVHUkVTSUEKIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMKYXR0YWNoKMO6ZGFqZSkKbW9kZWwgPC0gbG0oUG9wdWxhdGlvbi4yMDI1IH4gRmVydC4uUmF0ZSArIE1lZGlhbi5BZ2UgKyBNaWdyYW50cy4ubmV0LiwgCiAgICAgICAgICAgIGRhdGEgPSBkYXRhX3NlbGVjdGVkKQpzdW1tYXJ5KG1vZGVsKQpgYGAKClRlc3RvdmHFpSwgxI1pIGplIG1vZGVsIHYgc3Byw6F2bmVqIGZ1bmvEjW5laiBmb3JtZSAodC4gai4gxI1pIGplIGxpbmXDoXJuYSDFoXBlY2lmaWvDoWNpYSB2aG9kbsOhLCBhbGVibyDEjWkgYnkgc3RlIG1hbGkgdHJhbnNmb3Jtb3ZhxaUgcHJlbWVubsOpLCBuYXByw61rbGFkIHBvbW9jb3UgbG9nYXJpdG1vdiBhbGVibyBtb2NuaW5hbWkpLCBtb8W+bm8gdnlrb25hxaUgdmlhY2Vyw71taSBzcMO0c29ibWkuCgojIyMgMS4gVGVzdCBSRVNFVCAodGVzdCBjaHlieSDFoXBlY2lmaWvDoWNpZSBSYW1zZXlobyByZWdyZXNuZWogcm92bmljZSAtIFJhbXNleSBSZXNldCBUZXN0KQoKSWRlIG8gbmFqxaF0YW5kYXJkbmVqxaHDrSBmb3Jtw6FsbnkgdGVzdCBuZXNwcsOhdm5laiDFoXBlY2lmaWvDoWNpZSBmdW5rxI1uZWogZm9ybXkgYWxlIGTDoSBzYSBwb3XFvmnFpSBhaiBwcmUgcHLDrXBhZHksIGFrIHNtZSBuZcWhcGVjaWZpa292YWxpIHbFoWV0a3kgdnlzdmV0xL51asO6Y2UgcHJlbWVubsOpLgoKTXnFoWxpZW5rYTogTmVjaCBww7R2b2Ruw70gbW9kZWwgbcOhIHR2YXIKJCR5X3QgPSBcYmV0YV8wICsgXGJldGFfMSB4X3t0MTB9ICsgXGRvdHMgK1xiZXRhX2sgeF97dGt9ICsgdV90JCQKQWsgamUgdsOhxaEgbW9kZWwgc3Byw6F2bmUgxaFwZWNpZmlrb3ZhbsO9LCBwb3RvbSBwcmlkYW7DrW0gbW9jbsOtbiB2eXJvdm5hbsO9Y2ggaG9kbsO0dCAobmFwci4gJFxoYXQgeV90XjIkLCAkXGhhdHt5fV90XjMkKSBieSBzYSBww7R2b2Ruw70gbW9kZWwgbmVtYWwgcG9kc3RhdG5lIHpsZXDFoWnFpSwgdGVkYSBidWRlbWUgdGVzdG92YcWlIHDDtHZvZG7DvSBtb2RlbCB1dmVkZW7DvSB2ecWhxaFpZSBhIG1vZGVsCgokJHlfdCA9IFxiZXRhXzAgKyBcYmV0YV8xIHhfe3QxMH0gKyBcZG90cyArXGJldGFfayB4X3t0a30gKyBcZ2FtbWFfMlxoYXQgeV90XjIgKyBcZ2FtbWFfM1xoYXR7eX1fdF4zICsgdV90JCQKCkJ1ZGVtZSB0ZXN0b3ZhxaUgaHlwb3TDqXp1IAoKJEhfMDokIG1vZGVsIGplIHNwcsOhdm5lIMWhcGVjaWZpa292YW7DvSAoJFxnYW1tYV8yID0gXGdhbW1hXzMgPSAwJCkKCm9wcm90aQoKJEhfMTokIG1vZGVsIGplIG5lc3Byw6F2bmUgxaFwZWNpZmlrb3ZhbsO9ICgkXGdhbW1hXzIgXG5lIDAgIFxxdWFkIFx0ZXh0e2FsZWJvfSAgXHF1YWQgXGdhbW1hXzMgXG5lIDAkKQoKYGBge3IgcmVzZXRfdGVzdCwgbWVzc2FnZT1GQUxTRX0KbGlicmFyeShsbXRlc3QpCgojIHR2b2ogbW9kZWw6Cm1vZGVsIDwtIGxtKFBvcHVsYXRpb24uMjAyNSB+IEZlcnQuLlJhdGUgKyBNZWRpYW4uQWdlICsgTWlncmFudHMuLm5ldC4sIAogICAgICAgICAgICBkYXRhID0gZGF0YV9zZWxlY3RlZCkKCiMgUkVTRVQgdGVzdCDigJMgdGVzdCBuZXNwcsOhdm5laiDFoXBlY2lmaWvDoWNpZSBtb2RlbHUKcmVzZXRfcmVzdWx0cyA8LSByZXNldHRlc3QobW9kZWwsIHBvd2VyID0gMjozLCB0eXBlID0gImZpdHRlZCIpCnJlc2V0X3Jlc3VsdHMKCmBgYAoKKipJbnRlcnByZXTDoWNpYToqKgrwn6eqIFJFU0VUIHRlc3Qg4oCTIGtvbnRyb2xhIMWhcGVjaWZpa8OhY2llIG1vZGVsdQoKVsO9c2xlZG9rIFJFU0VUIHRlc3R1OgoKLSAqKlJFU0VUID0gMC45NDI4KiogIAotICoqcC12YWx1ZSA9IDAuMzkxMSoqCgpLZcSPxb5lIHAtdmFsdWUgamUgKip2ecWhxaFpYSBha28gMC4wNSoqLCAqbmV6YW1pZXRhbWUgbnVsb3bDuiBoeXBvdMOpenUqLCDFvmUgbW9kZWwgamUgc3Byw6F2bmUgxaFwZWNpZmlrb3ZhbsO9LiAgCgrinqHvuI8gKipNb2RlbCBuZXByZXVrYXp1amUgY2h5Ym7DuiBmdW5rxI1uw7ogZm9ybXUuKiogIArinqHvuI8gKipOaWUgamUgcG90cmVibsOpIHByaWTDoXZhxaUgbmVsaW5lw6FybmUgxI1sZW55IGFuaSDEj2FsxaFpZSBwcmVtZW5uw6kuKioKCk1vZGVsIHBvZMS+YSBSRVNFVCB0ZXN0dSAqKnpvZHBvdmVkw6EgdmhvZG5laiDFoXBlY2lmaWvDoWNpaSoqLgoKCiMjIyAyLiBHcmFmaWNrw6EgYW5hbMO9emEKIyMjIyBHcmFmICpSZXNpZHVhbHMgdnMuIEZpdHRlZCoKCkdyYWZpY2vDoSBhbmFsw716YSB2esWlYWh1IG1lZHppIHZ5cm92bmFuw71taSBob2Rub3RhbWkgbsOhaG9kbmVqIHByZW1lbm5laiBhIHJlesOtZHVhbWk6CgpgYGB7cn0KcGxvdChtb2RlbCwgd2hpY2ggPSAxKQpgYGAKCiMjIyDwn5OKIEludGVycHJldMOhY2lhIGdyYWZ1ICpSZXNpZHVhbHMgdnMuIEZpdHRlZCoKCk5hIGdyYWZlICpSZXNpZHVhbHMgdnMuIEZpdHRlZCogc2kgdsWhw61tYW1lIHJvemxvxb5lbmllIHJlemlkdcOtIG9rb2xvIGhvcml6b250w6FsbmVqIMSNaWFyeS4gIApaIG7DocWhaG8gZ3JhZnUgbW/Fvm5vIHBvem9yb3ZhxaUgbmFzbGVkb3Zuw6k6CgotIFbDpMSNxaFpbmEgcmV6aWR1w60gc2EgbmFjaMOhZHphICoqYmzDrXprbyBudWxvdmVqIG9zaSoqLCDEjW8gbmF6bmHEjXVqZSwgxb5lIG1vZGVsIG5ldnlrYXp1amUgc3lzdGVtYXRpY2vDqSBjaHlieS4KLSBSZXppZHXDoSBuZXZ5dHbDoXJhasO6IMW+aWFkbnkgdsO9cmF6bsO9IHR2YXIgKG5hcHIuIHBhcmFib2xhIGFsZWJvIGxpZXZpayksIHRha8W+ZSAqKm5pZSBzw7ogdmlkaXRlxL5uw6kgem7DoW1reSBuZWxpbmVhcml0eSoqLgotIE5lb2JqYXZ1amUgc2EgYW5pIHR5cGlja8O9IOKAnnJvesWhaXJ1asO6Y2kgc2EgbGlldmlr4oCcLCDEjWnFvmUgKipoZXRlcm9za2VkYXN0aWNpdGEgbmllIGplIHZpenXDoWxuZSB6cmVqbcOhKiouCi0gViBncmFmZSBzYSB2eXNreXR1amUgbmlla2/EvmtvIG9kxL5haGzDvWNoIGJvZG92IChleHRyw6ltbmUgxaF0w6F0eSksIMSNbyBqZSBwcmkgZGVtb2dyYWZpY2vDvWNoIGTDoXRhY2ggYmXFvm7DqSBhIG5lb8SNYWvDoXZhIHNhLCDFvmUgYnkgem5laG9kbm90aWxpIGNlbMO9IG1vZGVsLgoKIyMjIOKchSBaw6F2ZXIKTmEgesOha2xhZGUgZ3JhZmlja2VqIGRpYWdub3N0aWt5IG1vxb5ubyBwb3ZlZGHFpSwgxb5lICoqbW9kZWwgbmV2eWthenVqZSB6w6F2YcW+bsOpIMWhdHJ1a3R1csOhbG5lIHByb2Jsw6lteSoqLiAgClNwcsOhdmFuaWUgcmV6aWR1w60gamUgcHJpbWVyYW5lIG7DoWhvZG7DqSwgxI1vIHBvZHBvcnVqZSB6w6F2ZXJ5IGFqIHogUkVTRVQgdGVzdHUuCgoKCiMjIyMgR3JhZnkgQytSICoqClTDoXRvIGFuYWzDvXphIG7DoW0gbcO0xb5lIHBvbcO0Y8WlIHByaSBoxL5hZGFuw60gb2Rwb3ZlZGUgbmEgb3TDoXprdSwga3RvcsO6IHByZW1lbm7DuiBieSBzbWUgbWFsaSB0cmFuc2ZvbW92YcWlIHBvbW9jb3UgbmVqYWtlaiB6bsOhbWVqIGZ1bmtjaWUuIFZ5Y2jDoWR6YWptZSB6IHDDtHZvZG5laiByb3ZuaWNlCgokJHlfdCA9IFxiZXRhXzAgKyBcYmV0YV8xIHhfe3QxfSArIFxkb3RzICtcYmV0YV9rIHhfe3RrfSArIHVfdCQkClTDunRvIHJvdm5pY3UgbmFqcHJ2IG9kaGFkbmVtZSBhIHBvdG9tIHZ5a3Jlc8S+dWplbWUgZ3JhZnksIGtkZSB2w71yYXogY29tcG9uZW50K3Jlc2lkdWFsIChDK1IpIHBsb3QgdnlrcmVzxL51amUgbmEgenZpc2xlaiBvc2kgJFxoYXR7XGJldGF9X2l4X3t0aX0rZV90JCBhIG5hIHZvZG9yb3ZuZWogb3NpIHZ5a3Jlc8S+dWplIGhvZG5vdHkgJHhfe3RpfSQKClRpZXRvIGdyYWZ5IHBvbcOhaGFqw7ogaWRlbnRpZmlrb3ZhxaUgbmVsaW5lw6FybmUgdnrFpWFoeSBwcmUga2HFvmTDvSByZWdyZXNvcjoKCmBgYHtyfQpjYXI6OmNyUGxvdHMobW9kZWwpCgpgYGAKIyMjIPCfk4ogSW50ZXJwcmV0w6FjaWEgQ29tcG9uZW50ICsgUmVzaWR1YWwgKEMrUikgZ3JhZm92CgpDaWXEvm9tIEMrUiBncmFmb3YgamUgb3ZlcmnFpSwgxI1pIGplIHZ6xaVhaCBtZWR6aSBqZWRub3RsaXbDvW1pIHJlZ3Jlc29ybWkgYSB6w6F2aXNsb3UgcHJlbWVubm91IGxpbmXDoXJueSwgYWxlYm8gxI1pIGJ5IG1vaGxhIGJ5xaUgdmhvZG7DoSB0cmFuc2Zvcm3DoWNpYSAobG9nYXJpdG11cywgbW9jbmluYSBhIHBvZC4pLiAgCk5pxb7FoWllIHV2w6FkemFtIGludGVycHJldMOhY2l1IHByZSBrYcW+ZMO9IHJlZ3Jlc29yLgoKLS0tCgojIyMgKiox77iP4oOjIFByZW1lbm7DoSAqRmVydC4uUmF0ZSoqKgotIEtyaXZrYSBqZSB0YWttZXIgaG9yaXpvbnTDoWxuYSwgcyBtaW5pbcOhbG55bWkgb2RjaMO9bGthbWkuCi0gTmV2em5pa8OhIMW+aWFkbnkgdsO9cmF6bsO9IG5lbGluZcOhcm55IHZ6b3IuCgoqKuKeoe+4jyBMaW5lw6FybnkgdHZhciBqZSBwb3N0YcSNdWrDumNpLCB0cmFuc2Zvcm3DoWNpYSBuaWUgamUgcG90cmVibsOhLioqCgotLS0KCiMjIyAqKjLvuI/ig6MgUHJlbWVubsOhICpNZWRpYW4uQWdlKioqCi0gS3JpdmthIGplIHJvdm5ha28gdmXEvm1pIHBsb2Now6EgYSBiZXogbsOhem5ha3UgemFrcml2ZW5pYS4KLSBCb2RvdsOpIGhvZG5vdHkgc2Egcm96a2xhZGFqw7ogcm92bm9tZXJuZSBva29sbyDEjWlhcnkuCgoqKuKeoe+4jyBMaW5lw6FybmEgxaFwZWNpZmlrw6FjaWEgamUgdmhvZG7DoSwgdHJhbnNmb3Jtw6FjaWEgbmllIGplIHBvdHJlYm7DoS4qKgoKLS0tCgojIyMgKioz77iP4oOjIFByZW1lbm7DoSAqTWlncmFudHMuLm5ldC4qKioKLSBLcml2a2EgdWthenVqZSBqZW1uZSBzdMO6cGFqw7pjaSB0dmFyLCBuYWptw6QgcHJpIHZ5xaHFocOtY2ggaG9kbm90w6FjaCByZWdyZXNvcmEuCi0gVmlkaXRlxL5uw6EgamUgbWllcm5lIHbDpMSNxaFpYSB2YXJpYWJpbGl0YSBib2RvdiB2IHBvcm92bmFuw60gcyBvc3RhdG7DvW1pIHByZW1lbm7DvW1pLgotIElkZSB0YWsgbyBuYWp2w71yYXpuZWrFocOtIChob2NpIHN0w6FsZSBuaWUgdmXEvmvDvSkgb2RrbG9uIG9kIGxpbmVhcml0eS4KCioq4p6h77iPIE1vxb5uw6Ega2FuZGlkw6F0a2EgbmEgdHJhbnNmb3Jtw6FjaXUgKG5hcHIuIGxvZ2FyaXRtdXMpLCBhbGUgb2RrbG9uIG5pZSBqZSBkcmFtYXRpY2vDvSBhIG1vZGVsIGZ1bmd1amUgYWogYmV6IMO6cHJhdi4qKgoKLS0tCgojIyMg4pyFICoqWmhybnV0aWUqKgo+IEMrUiBncmFmeSBuYXpuYcSNdWrDuiwgxb5lIHJlZ3Jlc29yeSAqRmVydC4uUmF0ZSogYSAqTWVkaWFuLkFnZSogbWFqw7ogbGluZcOhcm55IHZ6xaVhaCBzbyB6w6F2aXNsb3UgcHJlbWVubm91LiBQcmVtZW5uw6EgKk1pZ3JhbnRzLi5uZXQuKiB1a2F6dWplIG1pZXJuZSBuZWxpbmXDoXJueSB0cmVuZCwgYWxlIG5pZSBuYXRvxL5rbyB2w71yYXpuw70sIGFieSBib2xvIG5ldnlobnV0bsOpIG1lbmnFpSDFoXBlY2lmaWvDoWNpdSBtb2RlbHUuIENlbGtvdm8gZ3JhZnkgbmVwb3VrYXp1asO6IG5hIHBvdHJlYnUgesOhc2FkbsO9Y2ggdHJhbnNmb3Jtw6FjacOtIHByZW1lbm7DvWNoLgoKCiMjIDMuIE5lbGluZcOhcm5hIMWhcGVjaWZpa8OhY2lhCsSMYXN0b2tyw6F0IG3DtMW+ZW1lIGFqIHpsb8W+aXRlasWhaWUgbmVsaW5lw6FybmUgdnrFpWFoeSBtb2RlbG92YcWlIHMgcG9tb2NvdSBpY2ggYXByb3hpbcOhY2llIHMgcG9seW7Ds21vbSwgdGVkYSB2IHByw61wYWRlIGt2YWRyYXRpY2vDvWNoIMSNbGVub3YKCiQkeV90ID0gXGJldGFfMCArIFxiZXRhXzEgeF97dDEwfSArIFxkb3RzICtcYmV0YV9rIHhfe3RrfSArIFxkb3RzICsgXGdhbW1hX2lcaGF0IHhfe2lrfV4yICsgXGRvdHMgKyBcZ2FtbWFfalxoYXQgeF97amt9XjIgKyBcZG90cyArIHVfdCQkClByw61rbGFkIG5hIHTDunRvIG1vZGlmaWvDoWNpdSB1dmlkw61tZSBuacW+xaFpZS4KCiMjIDQuIFBvcm92bmFuaWUgesOha2xhZG7DqWhvIGEgbW9kaWZpa292YW7DqWhvIG1vZGVsdQoKTmEgesOha2xhZGUgZ3JhZm92IENvbXBvbmVudCArIFJlc2lkdWFsIHNtZSBpZGVudGlmaWtvdmFsaSwgxb5lIG5hanbDpMSNxaHDrSBvZGtsb24gb2QgbGluZWFyaXR5IHZ5a2F6dWrDuiBwcmVtZW5uw6kgTWVkaWFuLkFnZSBhIE1pZ3JhbnRzLi5uZXQuLiBUaWV0byBwcmVtZW5uw6kgbmV2eXR2w6FyYWrDuiBzdHJpa3RuZSBsaW5lw6FybnkgdnrFpWFoIHNvIHrDoXZpc2xvdSBwcmVtZW5ub3UgUG9wdWxhdGlvbi4yMDI1LCDEjW8gbmF6bmHEjXVqZSBtb8W+bsO6IHBvdHJlYnUgZG9wbG5lbmlhIGt2YWRyYXRpY2vDvWNoIMSNbGVub3YuCgpQcmV0byBwcmVkcG9rbGFkw6FtZSwgxb5lIHByaSBuZWxpbmXDoXJueWNoIMO6cHJhdsOhY2ggcMO0dm9kbsOpaG8gbW9kZWx1IGTDtGpkZSBrIHpsZXDFoWVuaXUgamVobyDFoXBlY2lmaWvDoWNpZSBwcsOhdmUgcG8gemF2ZWRlbsOtIGt2YWRyw6F0b3YgcHJlbWVubsO9Y2ggTWVkaWFuLkFnZcKyIGEgTWlncmFudHMuLm5ldC7Csi4gSWNoIHNwcsOhdmFuaWUgdiBDK1IgZ3JhZm9jaCBuYXpuYcSNb3ZhbG8gbWllcm5lIHpha3JpdmVuaWUsIGt0b3LDqSBzYSB2w71yYXpuZWrFoWllIG9kY2h5xL5vdmFsbyBvZCBwcmlhbWt5LgoKQWsgbcOhIHRyYW5zZm9ybW92YW7DvSBtb2RlbCB2ecWhxaHDrSB1cHJhdmVuw70ga29lZmljaWVudCBkZXRlcm1pbsOhY2llICRSXjJfe2Fkan0kLCBsZXDFoWl1IMWhdGF0aXN0aWNrw7ogdsO9em5hbW5vc8WlIGEgesOhcm92ZcWIIFJFU0VUIHRlc3QgbmVwb3R2cmTDrSBuZXNwcsOhdm51IMWhcGVjaWZpa8OhY2l1LCBtw7TFvmVtZSBub3bDvSBtb2RlbCBwb3Zhxb5vdmHFpSB6YSB2aG9kbmVqxaHDrS4gT2Rwb3LDusSNYW1lIHbDvXNsZWRreSDEj2FsZWogcG9kcG9yacWlIGFqIHBvcm92bmFuw61tIG9ib2NoIG1vZGVsb3YgcG9tb2NvdSBBTk9WQSB0ZXN0dSwga3RvcsO9IG92ZXLDrSwgxI1pIG3DoSByb3rFocOtcmVuw70gbW9kZWwgxaF0YXRpc3RpY2t5IHbDvXpuYW1uZSBsZXDFoWl1IHbDvWtvbm5vc8WlLgoKYGBge3J9CiMgWsOha2xhZG7DvSBsaW5lw6FybnkgbW9kZWwKbW9kZWwgPC0gbG0oUG9wdWxhdGlvbi4yMDI1IH4gMSArIEZlcnQuLlJhdGUgKyBNZWRpYW4uQWdlICsgTWlncmFudHMuLm5ldC4sIAogICAgICAgICAgICBkYXRhID0gZGF0YV9zZWxlY3RlZCkKCiMgTW9kZWwgcyBrdmFkcmF0aWNrw71taSDEjWxlbm1pIG5hIHrDoWtsYWRlIEMrUiBncmFmb3YKbW9kZWxfa3ZhZHIgPC0gbG0oUG9wdWxhdGlvbi4yMDI1IH4gMSArIEZlcnQuLlJhdGUgKyAKICAgICAgICAgICAgICAgICAgICBNZWRpYW4uQWdlICsgSShNZWRpYW4uQWdlXjIpICsKICAgICAgICAgICAgICAgICAgICBNaWdyYW50cy4ubmV0LiArIEkoTWlncmFudHMuLm5ldC5eMiksCiAgICAgICAgICAgICAgICAgIGRhdGEgPSBkYXRhX3NlbGVjdGVkKQoKIyBWw71zdHVweSBtb2RlbHUKc3VtbWFyeShtb2RlbF9rdmFkcikKCiMgUG9yb3ZuYW5pZSB6w6FrbGFkbsOpaG8gYSBuZWxpbmXDoXJuZWhvIG1vZGVsdQphbm92YShtb2RlbCwgbW9kZWxfa3ZhZHIpCgojIFJFU0VUIHRlc3QgcHJlIG5lbGluZcOhcm5lIHJvesWhw61yZW7DvSBtb2RlbApyZXNldHRlc3QobW9kZWxfa3ZhZHIpCgpgYGAKClRha3RvIG1vZGlmaWtvdmFuw70gbW9kZWwsIHYga3Rvcm9tIHNtZSBkb3BsbmlsaSBrdmFkcsOhdCBwcmVtZW5uw71jaCAqTWVkaWFuLkFnZSogYSAqTWlncmFudHMuLm5ldC4qLCB2xaFhayBuZW96bmHEjXVqZSDFvmlhZG55IHoga3ZhZHJhdGlja8O9Y2ggxI1sZW5vdiB6YSDFoXRhdGlzdGlja3kgdsO9em5hbW7DvSAocC1ob2Rub3R5IHPDuiB2w71yYXpuZSB2w6TEjcWhaWUgYWtvIDAsMDUpLiBaw6Fyb3ZlxYggbmVkb2Now6FkemEgayB6bGVwxaFlbml1IHVwcmF2ZW7DqWhvIGtvZWZpY2llbnR1IGRldGVybWluw6FjaWUg4oCTIG5hb3BhaywgamVobyBob2Rub3RhIGtsZXNsYSBuYSBwcmlibGnFvm5lICRSXjJfe1x0ZXh0e2Fkan19IFxhcHByb3ggLTB7Ln0wMDQ2JC4KCkFqIHBvcm92bmFuaWUgbW9kZWxvdiBwb21vY291IEFOT1ZBIChwLWhvZG5vdGEgJFxhcHByb3ggMHsufTgwJCkgYSBSRVNFVCB0ZXN0dSAocC1ob2Rub3RhICRcYXBwcm94IDB7Ln00NyQpIHVrYXp1amUsIMW+ZSBrdmFkcmF0aWNrw70gbW9kZWwgbmllIGplIGxlcMWhw60gbmXFviBww7R2b2Ruw70gbGluZcOhcm55IG1vZGVsLiBWIMSPYWzFoWVqIGFuYWzDvXplIHByZXRvIHByYWN1amVtZSBzIGplZG5vZHVjaMWhw61tIGxpbmXDoXJueW0gbW9kZWxvbSBiZXoga3ZhZHJhdGlja8O9Y2ggxI1sZW5vdi4KCmBgYHtyfQptb2RlbF9rdmFkciA8LSBsbShQb3B1bGF0aW9uLjIwMjUgfiAxICsgRmVydC4uUmF0ZSArIE1lZGlhbi5BZ2UgKyBNaWdyYW50cy4ubmV0LiArCiAgICAgICAgICAgICAgICAgICAgSShNZWRpYW4uQWdlXjIpICsgSShNaWdyYW50cy4ubmV0Ll4yKSwKICAgICAgICAgICAgICAgICAgZGF0YSA9IGRhdGFfc2VsZWN0ZWQpCgpzdW1tYXJ5KG1vZGVsX2t2YWRyKQoKYGBgCiMjIyBQb3Jvdm5hbmllIHrDoWtsYWRuw6lobyBhIGt2YWRyYXRpY2t5IG1vZGlmaWtvdmFuw6lobyBtb2RlbHUKCkRvIG1vZGVsdSBzbWUgcHJpZGFsaSBrdmFkcmF0aWNrw6kgxI1sZW55IHByZW1lbm7DvWNoIGBNZWRpYW4uQWdlYCBhIGBNaWdyYW50cy4ubmV0LmAgcyBjaWXEvm9tCnphY2h5dGnFpSBtb8W+bsOpIG5lbGluZcOhcm5lIHZ6xaVhaHkuIFbDvXNsZWRreSB2xaFhayB1a2F6dWrDuiwgxb5lIGFuaSBqZWRlbiB6IHTDvWNodG8Ka3ZhZHJhdGlja8O9Y2ggxI1sZW5vdiBuaWUgamUgxaF0YXRpc3RpY2t5IHbDvXpuYW1uw70gKHbFoWV0a3kgcC1ob2Rub3R5IHPDuiB2w71yYXpuZSB2w6TEjcWhaWUgYWtvIDAuMDUpLgoKVXByYXZlbsO9IGtvZWZpY2llbnQgZGV0ZXJtaW7DoWNpZSB6b3N0YWwgdiBwb2RzdGF0ZSBuZXptZW5lbsO9IGEgbcOhIGhvZG5vdHUgIAoqKiRSXjJfe2Fkan0gPSAtMC4wMDQ2JCoqLCDEjW8gbmF6bmHEjXVqZSwgxb5lIGt2YWRyYXRpY2t5IHJvesWhw61yZW7DvSBtb2RlbCBuZXZ5c3ZldMS+dWplCnZhcmlhYmlsaXR1IGTDoXQgbGVwxaFpZSBha28gcMO0dm9kbsO9IG1vZGVsLgoKWmF2ZWRlbmllIGt2YWRyYXRpY2vDvWNoIMSNbGVub3YgcHJldG8gKipuZXByaW5pZXNsbyB6bGVwxaFlbmllKiogYSB2IMSPYWzFoWVqIGFuYWzDvXplCmJ1ZGVtZSBwb2tyYcSNb3ZhxaUgcyBww7R2b2Ruw71tIGxpbmXDoXJueW0gbW9kZWxvbS4KCiMjIyA1LiBQb3XFvml0aWUgcm96xaHDrXJlbsOpaG8gUkVTRVQgdGVzdHUKYGBge3J9Cm1vZGVsX3JvenNpcmVueSA8LSBsbSgKICBQb3B1bGF0aW9uLjIwMjUgfiAKICAgIEZlcnQuLlJhdGUgKwogICAgTWVkaWFuLkFnZSArCiAgICBNaWdyYW50cy4ubmV0LiArCiAgICBJKE1lZGlhbi5BZ2VeMikgKwogICAgSShNaWdyYW50cy4ubmV0Ll4yKSwKICBkYXRhID0gZGF0YV9zZWxlY3RlZAopCgpzdW1tYXJ5KG1vZGVsX3JvenNpcmVueSkKCmBgYApWIHRvbXRvIGtyb2t1IHRlc3R1amVtZSwgxI1pIGt2YWRyYXRpY2vDqSDEjWxlbnkgKipNZWRpYW4uQWdlwrIqKiBhICoqTWlncmFudHMuLm5ldC7CsioqICAKcHJpbsOhxaFhasO6IGRvIG1vZGVsdSDFoXRhdGlzdGlja3kgdsO9em5hbW7DqSBpbmZvcm3DoWNpZS4gIApBayBieSBib2xpIHbDvXpuYW1uw6ksIG1hbGkgYnkgc21lIHV2YcW+b3ZhxaUgbmFkIGt2YWRyYXRpY2tvdSB0cmFuc2Zvcm3DoWNpb3UgdMO9Y2h0byBwcmVtZW5uw71jaC4KCk5hIHrDoWtsYWRlIHbDvXN0dXB1IGBzdW1tYXJ5KG1vZGVsX3JvenNpcmVueSlgIHbFoWFrIHZpZMOtbWUsIMW+ZToKCi0ga29lZmljaWVudCBwcmkgYEkoTWVkaWFuLkFnZV4yKWAgKipuaWUgamUgxaF0YXRpc3RpY2t5IHbDvXpuYW1uw70qKiAocCA9IDAuODQ5KSwKLSBrb2VmaWNpZW50IHByaSBgSShNaWdyYW50cy4ubmV0Ll4yKWAgKip0YWt0aWXFviBuaWUgamUgxaF0YXRpc3RpY2t5IHbDvXpuYW1uw70qKiAocCA9IDAuNTE0KS4KCmBgYHtyfQphbm92YShtb2RlbCxtb2RlbF9yb3pzaXJlbnkpCnJlc2V0dGVzdChtb2RlbF9yb3pzaXJlbnkpCmBgYApQcmkgUkVTRVQgdGVzdGUgdmlkw61tZSwgxb5lIHAtaG9kbm90YSAqKjAuNDc0MSoqIGplIHbDvXJhem5lIHZ5xaHFoWlhIGFrbyBobGFkaW5hIHbDvXpuYW1ub3N0aSAwLjA1LiAgClRvIHpuYW1lbsOhLCDFvmUgKipuZXphbWlldGFtZSBudWxvdsO6IGh5cG90w6l6dSBzcHLDoXZuZWogxaFwZWNpZmlrw6FjaWUgbW9kZWx1KiouCgpaw6Fyb3ZlxYggdsWhYWsgcGxhdMOtLCDFvmUgYW5pIHJvesWhw61yZW7DvSBtb2RlbCBzIGt2YWRyYXRpY2vDvW1pIMSNbGVubWkgbmVib2wgxaF0YXRpc3RpY2t5IHbDvXpuYW1uw70gIAooQU5PVkEgcCA9IDAuNzk1NiksIHRha8W+ZSAqKnByw61wYWRuw70gcHJvYmzDqW0gbmVzcHLDoXZuZWogxaFwZWNpZmlrw6FjaWUgbW9kZWx1IHNhIG5lb2RzdHLDoW5pbCoqLCAgCmFsZSB6w6Fyb3ZlxYggKipuZWJvbCBhbmkgcG90dnJkZW7DvSoqLiBaYXZlZGVuaWUga3ZhZHJhdGlja8O9Y2ggxI1sZW5vdiBuZXByaW5pZXNsbyB6bGVwxaFlbmllIG1vZGVsdS4KCgojIyMgNi4gVHJhbnNmb3Jtw6FjaWEgcG9tb2NvdSBkdW1teSBwcmVtZW5uZWogYSBsaW5lw6FybmVqIGxvbWVuZWogZnVua2NpZQoKUHJlZHBva2xhZGFqbWUsIMW+ZSBtw6FtZSBkdW1teSBwcmVtZW5uw7ogJERfdCQsIGt0b3LDoSBvYnNhaHVqZSBsZW4gbnVseSBhIGplZG5pxI1reS4gVGFrw6F0byBwcmVtZW5uw6Egc2EgZMOhIHZ5dcW+acWlIG1vZGVsb3ZhbmllIHpsb21vdiwgYSB0byBuYXByLgoKMS4gemxvbSB2IGF1dG9uw7Ntbm9tIMSNbGVuZSAkXGJldGFfMCQgYSB0byBuYXNsZWRvdm5vdSDFoXBlY2lmaWvDoWNpb3UKJCR5X3QgPSBcYmV0YV8wICsgXGJldGFfRCBEKyBcYmV0YV8xIHhfe3QxfSArIFxkb3RzICtcYmV0YV9rIHhfe3RrfSArIHVfdCQkCsSNbyBpbnRlcnByZXR1amVtZSBha28gcG9zdW4gcmVncmVzbmVqIHByaWFta3kgKHJlZ3Jlc25laiBuYWRyb3ZpbnkpIG8gJFxiZXRhX0QkIGplZG5vdGllayBwb3pkxLrFviB6dmlzbGVqIG9zaSBhIHRvIGxlbiB2IHBvem9yb3ZhbmlhY2gsIGFrIGplIHNwbG5lbsOhIHBvZG1pZW5rYSAkRF90ID0gMSQKMi4gemxvbSB2IHNrbG9uZSByZWdyZXNuZWogcHJpYW1reSAobmFkcm92aW55KSBhIHRvIGxlbiB2IHBvem9yb3ZhbmlhY2gsIGFrIGplIHNwbG5lbsOhIHBvZG1pZW5rYSAkRF90ID0gMSQsIMSNbyBkb3NpYWhuZW1lIG5hc2xlZG92bm91IMWhcGVjaWZpa8OhY2lvdQokJHlfdCA9IFxiZXRhXzAgKyAgXGJldGFfMSB4X3t0MX0gKyBcZG90cyArIFxiZXRhX3tpfXhfe3RpfSArIFxiZXRhX3tEaX1EX3R4X3t0aX0rIFxkb3RzICsgXGJldGFfayB4X3t0a30gKyB1X3QkJAprZGUgdGVkYSBza2xvbiBwcmlhbWt5IHBvemTEusW+IHByZW1lbm5lICR4X3t0aX0kIGplICRcYmV0YV9pJCBhbGUgbGVuIHYgcHLDrXBhZGUgJERfdD0wJCwgaW5hayBqZSB0ZW4gc2tsb24gcm92bsO9ICRcYmV0YV9pK1xiZXRhX3tEX2l9JC4KCkFrIHNpIHBvenJpZW1lIEMrUiBncmFmeSBwcmUgbmHFoWUgdnlzdmV0xL51asO6Y2UgcHJlbWVubsOpLCB2aWTDrW1lLCDFvmUKbmFqdsO9cmF6bmVqxaFpZSBvZGNow71sa3kgb2QgbGluZWFyaXR5IHNhIG9iamF2dWrDuiBwcmkgcHJlbWVubsO9Y2gKKk1pZ3JhbnRzLi5uZXQuKiBhICpNZWRpYW4uQWdlKi4gVnlyb3ZuYW7DoSBrcml2a2EgcHJpIG9ib2NoIHByZW1lbm7DvWNoIG5hem5hxI11amUgbWllcm5lIHpha3JpdmVuaWUsIG5ham3DpCBwcmkgZXh0csOpbW5lasWhw61jaCBob2Rub3TDoWNoLCDEjW8gbcO0xb5lIHNpZ25hbGl6b3ZhxaUgcG90cmVidSBuZWxpbmXDoXJuZWogw7pwcmF2eSAodC5qLiB6YXZlZGVuaWUga3ZhZHJhdGlja8OpaG8gxI1sZW5hKS4gUHJldG8gc21lIGRvIG1vZGVsdSB6YXJhZGlsaSBwcmVtZW5uw6kgKipJKE1lZGlhbi5BZ2XCsikqKiBhICoqSShNaWdyYW50cy4ubmV0LsKyKSoqLCBhYnkgc21lIG90ZXN0b3ZhbGksIMSNaSB0aWV0byBuZWxpbmXDoXJuZSBlZmVrdHkgZG9rw6HFvnUgemxlcMWhacWlIMWhcGVjaWZpa8OhY2l1IG1vZGVsdS4KIApLdmFudGlmaWt1am1lIHRlcmF6IG1vZGVsIHNvIHpsb21vbSB2IGF1dG9uw7Ntbm9tIMSNbGVub3ZpLiAgCktlxI/FvmUgcG9kxL5hIEMrUiBncmFmb3YgemF6bmFtZW7DoXZhbWUgbmVsaW5lw6FybmUgc3Byw6F2YW5pZSBwcmkgcHJlbWVubsO9Y2gKKk1pZ3JhbnRzLi5uZXQuKiwgemF2ZWRpZW1lIG5vdsO6IGR1bW15IHByZW1lbm7Duiwga3RvcsOhIHJvemRlbMOtIGtyYWppbnkgcG9kxL5hCsO6cm92bmUgbWlncsOhY2llLgoKTmVjaCAgCiREVU1fdCA9IDAkIHByZSBob2Rub3R5IE1pZ3JhbnRzLi5uZXQuIG5pxb7FoWllIGFrbyBtZWRpw6FuICAKYSAgCiREVU1fdCA9IDEkIHByZSBob2Rub3R5IE1pZ3JhbnRzLi5uZXQuIHZ5xaHFoWllIGFsZWJvIHJvdm7DqSBtZWRpw6FudS4KClRha3RvIGJ1ZGVtZSBtw7RjxaUgcG9zw7pkacWlLCDEjWkgc2EgaW50ZXJjZXB0IG1vZGVsdSB2w71yYXpuZSBtZW7DrSBwcmkgdnnFocWhw61jaApob2Rub3TDoWNoIG1pZ3LDoWNpZS4KCmBgYHtyfQojIHByYWggc2kgbcO0xb5lbWUgdXLEjWnFpSBha28gbWVkacOhbgp0aHJlc2hvbGQgPC0gbWVkaWFuKGRhdGFfc2VsZWN0ZWQkTWlncmFudHMuLm5ldC4sIG5hLnJtID0gVFJVRSkKCiMgZHVtbXkgcHJlbWVubsOhIHBvZMS+YSBwcmFodQpkYXRhX3NlbGVjdGVkJERVTSA8LSBpZmVsc2UoZGF0YV9zZWxlY3RlZCRNaWdyYW50cy4ubmV0LiA8IHRocmVzaG9sZCwgMCwgMSkKCiMgbW9kZWwgc28gemxvbW9tIHYgYXV0b27Ds21ub20gxI1sZW5vdmkKbW9kZWxfYXV0byA8LSBsbShQb3B1bGF0aW9uLjIwMjUgfiAxICsgRFVNICsgRmVydC4uUmF0ZSArIE1lZGlhbi5BZ2UgKwogICAgICAgICAgICAgICAgICAgTWlncmFudHMuLm5ldC4sIAogICAgICAgICAgICAgICAgIGRhdGEgPSBkYXRhX3NlbGVjdGVkKQoKc3VtbWFyeShtb2RlbF9hdXRvKQoKYGBgClphdmVkZW7DrW0gemxvbW92ZWogcHJlbWVubmVqIERVTSBkb8WhbG8gayBtaWVybmVtdSB6bGVwxaFlbml1IG1vZGVsdSwga2XEj8W+ZSBrb2VmaWNpZW50IHByaSBEVU0gdnnFoWllbCBuYSBobGFkaW5lIHbDvXpuYW1ub3N0aSAxMCAlIMWhdGF0aXN0aWNreSB2w716bmFtbsO9IChwIOKJiCAwLjA5NTUpLiBUbyBuYXpuYcSNdWplLCDFvmUgcHJlIGtyYWppbnkgbmFkIHp2b2xlbm91IGhyYW5pY291IGZlcnRpbGl0eSBzYSDDunJvdmXFiCBwb3B1bMOhY2llIHN5c3RlbWF0aWNreSBsw63FoWkgKG3DoSBpbsO9IGludGVyY2VwdCkuIE9zdGF0bsOpIHByZW1lbm7DqSBvc3RhbGkgCm5ldsO9em5hbW7DqSBhIHVwcmF2ZW7DvSBSwrIgem9zdGFsIHZlxL5taSBuw616a3kgKOKJiCAwLjAwOTk2KS4gQ2Vsa292w70gRi10ZXN0IG5hem5hxI11amUsIMW+ZSBtb2RlbCBha28gY2Vsb2sgbmllIGplIHbDvXpuYW1uw70gKHAg4omIIDAuMTc5NikuIFphdmVkZW5pZSB6bG9tb3ZlaiBwcmVtZW5uZWogcHJldG8gbmVwcmluaWVzbG8gesOhc2FkbsOpIHpsZXDFoWVuaWUga3ZhbGl0eSBtb2RlbHUuCiAKYGBge3J9Cm1vZGVsRF9za2xvbiA8LSBsbShQb3B1bGF0aW9uLjIwMjUgfiAxICsgRmVydC4uUmF0ZSArIEkoRFVNICogRmVydC4uUmF0ZSkgKwogICAgICAgICAgICAgICAgICAgICBNZWRpYW4uQWdlICsgTWlncmFudHMuLm5ldC4sIAogICAgICAgICAgICAgICAgICAgZGF0YSA9IGRhdGFfc2VsZWN0ZWQpCgpzdW1tYXJ5KG1vZGVsRF9za2xvbikKCmBgYAojIyMg8J+TjCBJbnRlcnByZXTDoWNpYSB2w71zbGVka292IG1vZGVsdSBzbyB6bG9tb20gdiBza2xvbmUgKGludGVyYWtjaWEgYERVTSAqIEZlcnQuLlJhdGVgKQoKViB0b210byBrcm9rdSBzbWUgZG8gbW9kZWx1IHphdmllZGxpICp6bWVudSBza2xvbnUqIHByZSBwcmVtZW5uw7ogKipGZXJ0Li5SYXRlKiogcG9tb2NvdSBpbnRlcmFrxI1uw6lobyDEjWxlbmEgYEkoRFVNICogRmVydC4uUmF0ZSlgLiBQcmVtZW5uw6EgKipEVU0qKiByb3pkZcS+dWplIHBvem9yb3ZhbmlhIG5hIGR2ZSBza3VwaW55IHBvZMS+YSB2b3ByZWQgdXLEjWVuZWogaHJhbmljZSBhIHRlc3R1amVtZSwgxI1pIGZlcnRpbGl0YSBvdnBseXbFiHVqZSB2ZcS+a29zxaUgcG9wdWzDoWNpZSByb3pkaWVsbmUgdiB0w71jaHRvIGR2b2NoIHNrdXBpbsOhY2guCgotLS0KCiMjIyAqKvCfk4ogVsO9c2xlZGt5IHJlZ3Jlc27DqWhvIG1vZGVsdSoqCgotICoqRmVydC4uUmF0ZSoqICAKICAtIG9kaGFkOiBgLTMuMzQ4ZSswN2AgIAogIC0gcC1ob2Rub3RhOiBgMC4wNzE3YCAgCiAg4oaSIMO6xI1pbm9rIGplICpzbGFibyB2w716bmFtbsO9KiAocHJpYmxpxb5uZSBuYSAxMCAlIGhsYWRpbmUpLgoKLSAqKkludGVyYWtjaWEgYERVTSAqIEZlcnQuLlJhdGVgKiogIAogIC0gb2RoYWQ6IGAxLjU0OWUrMDdgICAKICAtIHAtaG9kbm90YTogYDAuMTUxN2AgIAogIOKGkiBpbnRlcmFrxI1uw70gZWZla3QgKm5pZSBqZSDFoXRhdGlzdGlja3kgdsO9em5hbW7DvSosIHRlZGEgc2tsb24gRmVydC4uUmF0ZSBzYSBwbyB6bWVuZSBEVU0gdsO9cmF6bmUgbmVtZW7DrS4KCi0gKipNZWRpYW4uQWdlKiogIAogIC0gcC1ob2Rub3RhOiBgMC4yNjA2YCAgCiAg4oaSIG5ldsO9em5hbW7DvSBlZmVrdC4KCi0gKipNaWdyYW50cy4ubmV0LioqICAKICAtIHAtaG9kbm90YTogYDAuMjM1MGAgIAogIOKGkiB0YWtpc3RvIG5ldsO9em5hbW7DvSBlZmVrdC4KCi0tLQoKIyMjICoq8J+TiCBIb2Rub3RlbmllIGt2YWxpdHkgbW9kZWx1KioKCi0gKipNdWx0aXBsZSBSLXNxdWFyZWQ6KiogYDAuMDIzOTNgICAKLSAqKkFkanVzdGVkIFItc3F1YXJlZDoqKiBgMC4wMDY4MDVgICAKICDihpIgbW9kZWwgdnlzdmV0xL51amUgKipsZW4gcHJpYmxpxb5uZSAyLDQgJSB2YXJpYWJpbGl0eSoqIHYgw7pkYWpvY2guCgotICoqRi10ZXN0IG1vZGVsdToqKiBwLWhvZG5vdGEgPSBgMC4yMzU3YCAgCiAg4oaSIG1vZGVsIGFrbyBjZWxvayAqKm5pZSBqZSDFoXRhdGlzdGlja3kgdsO9em5hbW7DvSoqLgoKLS0tCgojIyMgKirwn5OdIFrDoXZlcioqCgotIEludGVyYWvEjW7DvSDEjWxlbiBgRFVNICogRmVydC4uUmF0ZWAgKipuZXpsZXDFoWlsKioga3ZhbGl0dSBtb2RlbHUgYSBuaWUgamUgxaF0YXRpc3RpY2t5IHbDvXpuYW1uw70uICAKLSBOZWV4aXN0dWplIGTDtGtheiwgxb5lIGZlcnRpbGl0YSBtw6Egb2RsacWhbsO9IHZwbHl2IG5hIHBvcHVsw6FjaXUgdiByb2t1IDIwMjUgbWVkemkgZHZvbWkgc2t1cGluYW1pIGRlZmlub3ZhbsO9bWkgcG9kxL5hIHByZW1lbm5laiAqKkRVTSoqLiAgCi0gTW9kZWwgbcOhIHZlxL5taSBuw616a2UgaG9kbm90eSBcKFJeMlwpIGFqIFwoUl4yX3tcdGV4dHthZGp9fVwpLCDEjW8gem5hbWVuw6Egc2xhYsO6IHZ5c3ZldMS+b3ZhY2l1IHNjaG9wbm9zxaUuICAKLSAqKk1vZGVsIHNvIHpsb21vbSB2IHNrbG9uZSBwcmV0byBuZW9kcG9yw7rEjWFtZSBwb3XFvsOtdmHFpSBha28gZmluw6FsbnkgbW9kZWwuKioKCi0tLQoKCmBgYHtyfQphbm92YShtb2RlbCwgbW9kZWxEX3NrbG9uKQpyZXNldHRlc3QobW9kZWxEX3NrbG9uKQpgYGAKIyMjIPCfk4wgUG9yb3ZuYW5pZSBtb2RlbG92IHBvbW9jb3UgQU5PVkEgYSBSRVNFVCB0ZXN0dQoKTmEgb3ZlcmVuaWUsIMSNaSB6YXZlZGVuaWUgaW50ZXJha8SNbsOpaG8gxI1sZW5hIGBEVU0gKiBGZXJ0Li5SYXRlYCB2aWVkbG8gayB6bGVwxaFlbml1IMWhcGVjaWZpa8OhY2llIG1vZGVsdSwgc21lIHBvdcW+aWxpICoqQU5PVkEgdGVzdCoqIGEgbsOhc2xlZG5lIGFqICoqUkVTRVQgdGVzdCoqLgoKLS0tCgojIyMg8J+UjSAqKlbDvXNsZWRreSBBTk9WQSB0ZXN0dSoqCgpBTk9WQSBwb3Jvdm7DoXZhOgoKLSAqKk1vZGVsIDE6KiogIAogIGBQb3B1bGF0aW9uLjIwMjUgfiAxICsgRmVydC4uUmF0ZSArIE1lZGlhbi5BZ2UgKyBNaWdyYW50cy4ubmV0LmAgIAotICoqTW9kZWwgMiAocm96xaHDrXJlbsO9KToqKiAgCiAgYFBvcHVsYXRpb24uMjAyNSB+IDEgKyBGZXJ0Li5SYXRlICsgSShEVU0gKiBGZXJ0Li5SYXRlKSArIE1lZGlhbi5BZ2UgKyBNaWdyYW50cy4ubmV0LmAKClbDvXNsZWRvazoKCi0gKipGID0gMi4wNjk0KiosICAKLSAqKnAtaG9kbm90YSA9IDAuMTUxNyoqCgrwn5GJIEtlxI/FvmUgcC1ob2Rub3RhIGplICoqdsOkxI3FoWlhIGFrbyAwLjA1KiosICpyb3rFocOtcmVuw70gbW9kZWwgbmV2eWthenVqZSDFoXRhdGlzdGlja3kgdsO9em5hbW7DqSB6bGVwxaFlbmllKiBvcHJvdGkgesOha2xhZG7DqW11IG1vZGVsdS4gIApJbnRlcmFrxI1uw70gxI1sZW4gdGVkYSAqKm5lcHJpc3BlbCBrIGxlcMWhaWVtdSB2eXN2ZXRsZW5pdSB2YXJpYWJpbGl0eSoqIHYgZMOhdGFjaC4KCi0tLQoKIyMjIPCfp6ogKipSRVNFVCB0ZXN0IHByZSBtb2RlbCBzbyB6bG9tb20gdiBza2xvbmUqKgoKVsO9c2xlZG9rIFJFU0VUIHRlc3R1OgoKLSAqKlJFU0VUID0gMC45MjExNyoqICAKLSAqKmRmMSA9IDIsIGRmMiA9IDIyNioqICAKLSAqKnAtaG9kbm90YSA9IDAuMzk5NSoqCgrwn5GJIEtlxI/FvmUgcC1ob2Rub3RhIGplIG9ww6TFpSAqKm92ZcS+YSB2ecWhxaFpYSBha28gMC4wNSoqLCAqbmV6YW1pZXRhbWUgbnVsb3bDuiBoeXBvdMOpenUgc3Byw6F2bmVqIMWhcGVjaWZpa8OhY2llIG1vZGVsdSouICAKUkVTRVQgdGVzdCB0ZWRhICoqbmVpbmRpY3VqZSBjaHlibsO6IGZ1bmvEjW7DuiBmb3JtdSoqLCBhbGUgesOhcm92ZcWIICoqYW5pIG5lcG90dnJkenVqZSoqLCDFvmUgaW50ZXJha2NpYSBwcmluaWVzbGEgemxlcMWhZW5pZS4KCi0tLQoKIyMjIPCfk50gKipaw6F2ZXIqKgoKLSBBbmkgKipBTk9WQSoqLCBhbmkgKipSRVNFVCB0ZXN0KiogbmVwcmV1a8OhemFsaSwgxb5lIGJ5IHphdmVkZW5pZSBpbnRlcmFrxI1uw6lobyDEjWxlbmEgYERVTSAqIEZlcnQuLlJhdGVgIHByaXNwZWxvIGsgemxlcMWhZW5pdSBtb2RlbHUuICAKLSBNb2RlbCBzbyB6bG9tb20gdiBza2xvbmUgKipuaWUgamUgxaF0YXRpc3RpY2t5IGxlcMWhw60qKiBha28gcMO0dm9kbsO9IG1vZGVsLiAgCi0gTmVleGlzdHVqZSBkw7RrYXosIMW+ZSBmZXJ0aWxpdGEgbcOhICpvZGxpxaFuw70gdnBseXYqIG5hIHBvcHVsw6FjaXUgdiByw7R6bnljaCBza3VwaW7DoWNoIGRlZmlub3ZhbsO9Y2ggcHJlbWVubm91IERVTS4gIAotIFpvc3TDoXZhbWUgdGVkYSBwcmkgesOhdmVyZSwgxb5lICoqdGVudG8gbW9kZWwgbmllIGplIHZob2Ruw70gYWtvIGZpbsOhbG55KiogYSBuZXBvZHBvcnVqZSBoeXBvdMOpenUgbyB6bWVuZSBza2xvbnUuCgotLS0K