1 Wprowadzenie

Cel: wyznaczenie obszaru ufności dla dystrybuanty nieznanego rozkładu, a nie tylko oszacowania parametrów, od jakich zależą jej wartości.

  • Brzegi tego obszaru są wykresami funkcji „przedziałami stałych” (funkcji schodkowych).

  • Jeżeli przy wyznaczaniu pasma ufności dla dystrybuanty otrzymamy lewy kraniec przedziału będący liczbą ujemną, to zastępujemy ją przez zero.

  • Jeżeli otrzymamy prawy kraniec przedziału większy od jedności, to przyjmujemy, że jest on równy jeden.

  • Określenie obszaru ufności dla dystrybuanty w przedstawiony sposób polega na wyznaczeniu przedziałowego oszacowania dla każdej wartości dystrybuanty.

1.1 Funkcja CDF

Funkcja w programie R odpowiedzialna za estymację to np. CDF z pakietu spatstat. CDF jest metodą ogólną, z metodą dla klasy “gęstość”.

Oblicza ona skumulowaną funkcję rozkładu, której gęstość prawdopodobieństwa została oszacowana i zapisana w obiekcie f. Obiekt f musi należeć do klasy “gęstość” i zazwyczaj zostałby uzyskany z wywołania funkcji gęstość.

1.2 Funkcja kde

Pakiet R o nazwie snpar zawiera kilka uzupełniających metod statystyki nieparametrycznej, w tym test kwantylowy, test trendu Coxa-Stuarta, test przebiegów, test normalnego wyniku, estymację jądra PDF i CDF, estymację regresji jądra i test jądra Kołmogorowa-Smirnowa.

Funkcja kde zawiera obliczanie zarówno nieparametrycznego estymatora jądra funkcji gęstości prawdopodobieństwa (PDF) jak i funkcji rozkładu skumulowanego (CDF).

1.3 Przykład 1.

   b <- density(runif(10))
   f <- CDF(b)
   f(0.5)
## [1] 0.603946
   plot(f)

1.4 Przeczytaj

Przeczytaj artykuł naukowy “Kernel-smoothed cumulative distribution function estimation with akdensity” autorstwa Philippe Van Kerm.

1.5 Zadanie

Posłużymy się zbiorem danych diagnozy społecznej.

Na jego podstawie Twoim zadaniem jest oszacowanie rozkładu “p64 Pana/Pani wlasny (osobisty) dochod miesieczny netto (na reke)” według województw/płci.

Postaraj się oszacować zarówno rozkład gęstości jak i skumulowanej gęstości (dystrybuanty).

data("diagnoza")
data("diagnozaDict")

dane <- data.frame(dochod=diagnoza$gp64, 
                   plec=diagnoza$plec, 
                   woj=diagnoza$wojewodztwo)

dane <- dane %>% 
  drop_na(dochod, woj, plec)

dane$dochod <- as.numeric(dane$dochod)

Histogram rozkładu dochodu wg płci

ggplot(dane, aes(x = dochod, fill = plec)) +
  geom_histogram(position="dodge", alpha = 0.5)+
  labs(title = "Rozkład dochodów miesięcznych netto według płci")+
  facet_wrap(~ plec)
## `stat_bin()` using `bins = 30`. Pick better value with `binwidth`.

1.5.1 Rozkład gęstości

Estymacja gęstości, w przeciwieństwie do histogramów, tworzy bardziej płynny obraz rozkładu danych, nie dzieląc ich na sztywne kategorie. Dodatkowo uwypuklają nam się różnice w kształcie rozkładu między grupami.

1.5.1.1 Typ jądra

d_gaussian <- density(dane$dochod, kernel = "gaussian", bw = 3)
d_epanechnikov <- density(dane$dochod, kernel = "epanechnikov", bw = 3)
d_rectangular <- density(dane$dochod, kernel = "rectangular", bw = 3)
par(mfrow = c(3, 1))
plot(d_gaussian,main = "Default")
plot(d_epanechnikov, main = "Epanechnikov")
plot(d_rectangular, main = "Rectangular")

Z rozróżnieniem na płeć:

plot_g <- ggplot(dane, aes(x=dochod, fill=plec))+
  stat_density()+
  labs(title="Estymacja gęstości z jądrem Gaussa")
plot_g

plot_e <- ggplot(dane, aes(x=dochod, fill=plec))+
  stat_density(kernel = "epanechnikov")+
  labs(title="Estymacja gęstości z jądrem Epanechnikova")
plot_e

plot_t <- ggplot(dane, aes(x=dochod, fill=plec))+
  stat_density(kernel = "rectangular")+
  labs(title="Estymacja gęstości z jądrem prostokątnym")
plot_t

Wniosek: Różne typu jądra dają podobne wyniki, zatem do dalszej analizy wystarczy użyć jądra domyślnego - Gausowskiego.

1.5.1.2 Selekcja pasma

d_0 <- density(dane$dochod, bw = "nrd0")
plot(d_0, main = "Pasmo nrd0", col="yellowgreen")

d_scott <- density(dane$dochod, bw = "nrd")
plot(d_scott, main = "Pasmo Scotta", col='midnightblue')

d_ucv <- density(dane$dochod, bw = "ucv")
## Warning in bw.ucv(x): odnotowano wartość minimalną na jednym z końców zakresu
plot(d_ucv, main = "Pasmo UCV", col="coral")

d_SJ <- density(dane$dochod, bw = "SJ")
plot(d_SJ, main = "Pasmo Sheathera & Jonesa", col="darkcyan")

Wniosek: Szerokość pasma wpływa na wyniki oszacowania gestości. Metody SJ i UCV mają zbyt małą szerokośc pasma, zatem są nadmiernie dopasopwuje sie do krzywej.

Optymalnym wyborem może być reguła Scotta lub domyślna.

ggplot(dane, aes(x=dochod, fill=plec))+
  stat_density(bw = "nrd")+
  labs(title="Estymacja gęstości z pasmem Scotta z podziałem na płeć")

1.5.2 Oszacowanie skumulowanej gęstości

Dystrybuanta to funkcja, która opisuje prawdopodobieństwo, że zmienna losowa przyjmie wartość mniejszą lub równą danej wartości x.

1.5.2.1 Typ jądra

dystrybuanta_g <- approxfun(d_gaussian$x,
                          cumsum(d_gaussian$y)/sum(d_gaussian$y))

dystrybuanta_e <- approxfun(d_epanechnikov$x,
                          cumsum(d_epanechnikov$y)/sum(d_epanechnikov$y))

dystrybuanta_r <- approxfun(d_rectangular$x,
                          cumsum(d_rectangular$y)/sum(d_rectangular$y))

x_vals <- seq(min(dane$dochod), max(dane$dochod), length.out = 100)
par(mfrow = c(3, 1))
plot(x_vals, dystrybuanta_g(x_vals), pch=1,
     main = "CDF dla jądra Gaussowskiego", 
     xlab = "Dochód", ylab = "Dystrybuanta")
plot(x_vals, dystrybuanta_e(x_vals), pch=1,
     main = "CDF dla jądra Epanechnikova", 
     xlab = "Dochód", ylab = "Dystrybuanta")
plot(x_vals, dystrybuanta_r(x_vals), pch=1,
     main = "CDF dla jądra prostokątnego", 
     xlab = "Dochód", ylab = "Dystrybuanta")

1.5.2.2 Selekcja pasma

dystrybuanta_0 <- approxfun(d_0$x,
                          cumsum(d_0$y)/sum(d_0$y))

dystrybuanta_s <- approxfun(d_scott$x,
                          cumsum(d_scott$y)/sum(d_scott$y))

dystrybuanta_ucv <- approxfun(d_ucv$x,
                          cumsum(d_ucv$y)/sum(d_ucv$y))

dystrybuanta_SJ <- approxfun(d_SJ$x,
                          cumsum(d_SJ$y)/sum(d_SJ$y))

x_vals <- seq(min(dane$dochod), max(dane$dochod), length.out = 100)
plot(x_vals, dystrybuanta_0(x_vals), pch=1, 
     main = "CDF dla pasma nrd0", 
     xlab = "Dochód", ylab = "Dystrybuanta", 
     col = "yellowgreen", lwd = 2)

plot(x_vals, dystrybuanta_s(x_vals), pch=1, 
     main = "CDF dla pasma nrd0", 
     xlab = "Dochód", ylab = "Dystrybuanta", 
     col = "midnightblue", lwd = 2)

plot(x_vals, dystrybuanta_ucv(x_vals), pch=1, 
     main = "CDF dla pasma nrd0", 
     xlab = "Dochód", ylab = "Dystrybuanta", 
     col = "coral", lwd = 2)

plot(x_vals, dystrybuanta_SJ(x_vals), pch=1, 
     main = "CDF dla pasma nrd0", 
     xlab = "Dochód", ylab = "Dystrybuanta", 
     col = "darkcyan", lwd = 2)

Wniosek: Szerokość pasma znikomo wpływa na wyniki oszacowania dystrybuanty.

Estymacja gęstości i skumulowanej gęstości są potężnymi narzędziami do analizy danych. Różne typy jąder i metody doboru pasma mogą prowadzić do różnych rezultatów, co podkreśla znaczenie starannego wyboru metod analizy w badaniach statystycznych. Natomiast analizowane dane mają wartości odstające, które znacznie wpłynęły na analizę gęstości i dystrybuanty. Spowodowały one, że różnice pomiędzy różnymi pasmami czy jądrami, nie wpływaja istonie na analizę ( z wyjątkiem doboru pasma dla gęstości ).

LS0tDQp0aXRsZTogIk5pZWtsYXN5Y3puZSBtZXRvZHkgc3RhdHlzdHlraSINCnN1YnRpdGxlOiAiTmllcGFyYW1ldHJ5Y3puYSBlc3R5bWFjamEgZHlzdHJ5YnVhbnR5Ig0KYXV0aG9yOiAiTWFqYSBMZW1hxYRjenlrLCBKdWxpYSBCdWdhcnluIg0Kb3V0cHV0Og0KICBodG1sX2RvY3VtZW50Og0KICAgIHRoZW1lOiBjZXJ1bGVhbg0KICAgIGhpZ2hsaWdodDogdGV4dG1hdGUNCiAgICBmb250c2l6ZTogOHB0DQogICAgdG9jOiB0cnVlDQogICAgbnVtYmVyX3NlY3Rpb25zOiB0cnVlDQogICAgY29kZV9kb3dubG9hZDogdHJ1ZQ0KICAgIHRvY19mbG9hdDoNCiAgICAgIGNvbGxhcHNlZDogZmFsc2UNCmVkaXRvcl9vcHRpb25zOiANCiAgbWFya2Rvd246IA0KICAgIHdyYXA6IDcyDQotLS0NCg0KYGBge3Igc2V0dXAsIGluY2x1ZGU9RkFMU0V9DQprbml0cjo6b3B0c19jaHVuayRzZXQoZWNobyA9IFRSVUUpDQpsaWJyYXJ5KHNwYXRzdGF0KQ0KbGlicmFyeShkcGx5cikNCmlmICghcmVxdWlyZSgiZGV2dG9vbHMiKSkNCmluc3RhbGwucGFja2FnZXMoImRldnRvb2xzIikNCmRldnRvb2xzOjppbnN0YWxsX2dpdGh1YigiZGViaW5xaXUvc25wYXIiKQ0KDQpsaWJyYXJ5KHRpZHlyKQ0KbGlicmFyeShQb2dyb21jeURhbnljaCkNCmxpYnJhcnkoZ2dwbG90MikNCmBgYA0KDQojIFdwcm93YWR6ZW5pZQ0KDQpDZWw6IHd5em5hY3plbmllIG9ic3phcnUgdWZub8WbY2kgZGxhIGR5c3RyeWJ1YW50eSBuaWV6bmFuZWdvIHJvemvFgmFkdSwgYQ0KbmllIHR5bGtvIG9zemFjb3dhbmlhIHBhcmFtZXRyw7N3LCBvZCBqYWtpY2ggemFsZcW8xIUgamVqIHdhcnRvxZtjaS4NCg0KLSAgIEJyemVnaSB0ZWdvIG9ic3phcnUgc8SFIHd5a3Jlc2FtaSBmdW5rY2ppIOKAnnByemVkemlhxYJhbWkgc3RhxYJ5Y2giDQogICAgKGZ1bmtjamkgc2Nob2Rrb3d5Y2gpLg0KDQotICAgSmXFvGVsaSBwcnp5IHd5em5hY3phbml1IHBhc21hIHVmbm/Fm2NpIGRsYSBkeXN0cnlidWFudHkgb3RyenltYW15DQogICAgbGV3eSBrcmFuaWVjIHByemVkemlhxYJ1IGLEmWTEhWN5IGxpY3pixIUgdWplbW7EhSwgdG8gemFzdMSZcHVqZW15IGrEhQ0KICAgIHByemV6IHplcm8uDQoNCi0gICBKZcW8ZWxpIG90cnp5bWFteSBwcmF3eSBrcmFuaWVjIHByemVkemlhxYJ1IHdpxJlrc3p5IG9kIGplZG5vxZtjaSwgdG8NCiAgICBwcnp5am11amVteSwgxbxlIGplc3Qgb24gcsOzd255IGplZGVuLg0KDQotICAgT2tyZcWbbGVuaWUgb2JzemFydSB1Zm5vxZtjaSBkbGEgZHlzdHJ5YnVhbnR5IHcgcHJ6ZWRzdGF3aW9ueSBzcG9zw7NiDQogICAgcG9sZWdhIG5hIHd5em5hY3plbml1IHByemVkemlhxYJvd2VnbyBvc3phY293YW5pYSBkbGEga2HFvGRlaiB3YXJ0b8WbY2kNCiAgICBkeXN0cnlidWFudHkuDQoNCiMjIEZ1bmtjamEgQ0RGDQoNCkZ1bmtjamEgdyBwcm9ncmFtaWUgUiBvZHBvd2llZHppYWxuYSB6YSBlc3R5bWFjasSZIHRvIG5wLiBDREYgeiBwYWtpZXR1DQpzcGF0c3RhdC4gQ0RGIGplc3QgbWV0b2TEhSBvZ8OzbG7EhSwgeiBtZXRvZMSFIGRsYSBrbGFzeSAiZ8SZc3RvxZvEhyIuDQoNCk9ibGljemEgb25hIHNrdW11bG93YW7EhSBmdW5rY2rEmSByb3prxYJhZHUsIGt0w7NyZWogZ8SZc3RvxZvEhw0KcHJhd2RvcG9kb2JpZcWEc3R3YSB6b3N0YcWCYSBvc3phY293YW5hIGkgemFwaXNhbmEgdyBvYmlla2NpZSBmLiBPYmlla3QgZg0KbXVzaSBuYWxlxbxlxIcgZG8ga2xhc3kgImfEmXN0b8WbxIciIGkgemF6d3ljemFqIHpvc3RhxYJieSB1enlza2FueSB6DQp3eXdvxYJhbmlhIGZ1bmtjamkgZ8SZc3RvxZvEhy4NCg0KIyMgRnVua2NqYSBrZGUNCg0KUGFraWV0IFIgbyBuYXp3aWUgc25wYXIgemF3aWVyYSBraWxrYSB1enVwZcWCbmlhasSFY3ljaCBtZXRvZCBzdGF0eXN0eWtpDQpuaWVwYXJhbWV0cnljem5laiwgdyB0eW0gdGVzdCBrd2FudHlsb3d5LCB0ZXN0IHRyZW5kdSBDb3hhLVN0dWFydGEsIHRlc3QNCnByemViaWVnw7N3LCB0ZXN0IG5vcm1hbG5lZ28gd3luaWt1LCBlc3R5bWFjasSZIGrEhWRyYSBQREYgaSBDREYsIGVzdHltYWNqxJkNCnJlZ3Jlc2ppIGrEhWRyYSBpIHRlc3QgasSFZHJhIEtvxYJtb2dvcm93YS1TbWlybm93YS4NCg0KRnVua2NqYSBrZGUgemF3aWVyYSBvYmxpY3phbmllIHphcsOzd25vIG5pZXBhcmFtZXRyeWN6bmVnbyBlc3R5bWF0b3JhDQpqxIVkcmEgZnVua2NqaSBnxJlzdG/Fm2NpIHByYXdkb3BvZG9iaWXFhHN0d2EgKFBERikgamFrIGkgZnVua2NqaSByb3prxYJhZHUNCnNrdW11bG93YW5lZ28gKENERikuDQoNCiMjIFByenlrxYJhZCAxLg0KDQpgYGB7cn0NCiAgIGIgPC0gZGVuc2l0eShydW5pZigxMCkpDQogICBmIDwtIENERihiKQ0KICAgZigwLjUpDQogICBwbG90KGYpDQpgYGANCg0KIyMgUHJ6ZWN6eXRhag0KDQpQcnplY3p5dGFqIGFydHlrdcWCIG5hdWtvd3kgWyJLZXJuZWwtc21vb3RoZWQgY3VtdWxhdGl2ZSBkaXN0cmlidXRpb24NCmZ1bmN0aW9uIGVzdGltYXRpb24gd2l0aA0KYWtkZW5zaXR5Il0oaHR0cHM6Ly9qb3VybmFscy5zYWdlcHViLmNvbS9kb2kvcGRmLzEwLjExNzcvMTUzNjg2N1gxMjAxMjAwMzEzKQ0KYXV0b3JzdHdhIFBoaWxpcHBlIFZhbiBLZXJtLg0KDQojIyBaYWRhbmllDQoNClBvc8WCdcW8eW15IHNpxJkgemJpb3JlbSBkYW55Y2ggZGlhZ25venkgc3BvxYJlY3puZWouDQoNCk5hIGplZ28gcG9kc3Rhd2llIFR3b2ltIHphZGFuaWVtIGplc3Qgb3N6YWNvd2FuaWUgcm96a8WCYWR1ICJwNjQNClBhbmEvUGFuaSB3bGFzbnkgKG9zb2Jpc3R5KSBkb2Nob2QgbWllc2llY3pueSBuZXR0byAobmEgcmVrZSkiIHdlZMWCdWcNCndvamV3w7NkenR3L3DFgmNpLg0KDQpQb3N0YXJhaiBzacSZIG9zemFjb3dhxIcgemFyw7N3bm8gcm96a8WCYWQgZ8SZc3RvxZtjaSBqYWsgaSBza3VtdWxvd2FuZWoNCmfEmXN0b8WbY2kgKGR5c3RyeWJ1YW50eSkuDQoNCmBgYHtyIHphZGFuaWV9DQpkYXRhKCJkaWFnbm96YSIpDQpkYXRhKCJkaWFnbm96YURpY3QiKQ0KDQpkYW5lIDwtIGRhdGEuZnJhbWUoZG9jaG9kPWRpYWdub3phJGdwNjQsIA0KICAgICAgICAgICAgICAgICAgIHBsZWM9ZGlhZ25vemEkcGxlYywgDQogICAgICAgICAgICAgICAgICAgd29qPWRpYWdub3phJHdvamV3b2R6dHdvKQ0KDQpkYW5lIDwtIGRhbmUgJT4lIA0KICBkcm9wX25hKGRvY2hvZCwgd29qLCBwbGVjKQ0KDQpkYW5lJGRvY2hvZCA8LSBhcy5udW1lcmljKGRhbmUkZG9jaG9kKQ0KYGBgDQoNCioqSGlzdG9ncmFtIHJvemvFgmFkdSBkb2Nob2R1IHdnIHDFgmNpKioNCg0KYGBge3J9DQpnZ3Bsb3QoZGFuZSwgYWVzKHggPSBkb2Nob2QsIGZpbGwgPSBwbGVjKSkgKw0KICBnZW9tX2hpc3RvZ3JhbShwb3NpdGlvbj0iZG9kZ2UiLCBhbHBoYSA9IDAuNSkrDQogIGxhYnModGl0bGUgPSAiUm96a8WCYWQgZG9jaG9kw7N3IG1pZXNpxJljem55Y2ggbmV0dG8gd2VkxYJ1ZyBwxYJjaSIpKw0KICBmYWNldF93cmFwKH4gcGxlYykNCmBgYA0KDQojIyMgUm96a8WCYWQgZ8SZc3RvxZtjaQ0KDQpbRXN0eW1hY2phIGfEmXN0b8WbY2ksXXsudW5kZXJsaW5lfSB3IHByemVjaXdpZcWEc3R3aWUgZG8gaGlzdG9ncmFtw7N3LA0KdHdvcnp5IFtiYXJkemllaiBwxYJ5bm55IG9icmF6IHJvemvFgmFkdSBkYW55Y2hdey51bmRlcmxpbmV9LCBuaWUgZHppZWzEhWMNCmljaCBuYSBzenR5d25lIGthdGVnb3JpZS4gRG9kYXRrb3dvIHV3eXB1a2xhasSFIG5hbSBzacSZIHLDs8W8bmljZSB3DQprc3p0YcWCY2llIHJvemvFgmFkdSBtacSZZHp5IGdydXBhbWkuDQoNCiMjIyMgKipUeXAgasSFZHJhKioNCg0KYGBge3J9DQpkX2dhdXNzaWFuIDwtIGRlbnNpdHkoZGFuZSRkb2Nob2QsIGtlcm5lbCA9ICJnYXVzc2lhbiIsIGJ3ID0gMykNCmRfZXBhbmVjaG5pa292IDwtIGRlbnNpdHkoZGFuZSRkb2Nob2QsIGtlcm5lbCA9ICJlcGFuZWNobmlrb3YiLCBidyA9IDMpDQpkX3JlY3Rhbmd1bGFyIDwtIGRlbnNpdHkoZGFuZSRkb2Nob2QsIGtlcm5lbCA9ICJyZWN0YW5ndWxhciIsIGJ3ID0gMykNCmBgYA0KDQpgYGB7cn0NCnBhcihtZnJvdyA9IGMoMywgMSkpDQpwbG90KGRfZ2F1c3NpYW4sbWFpbiA9ICJEZWZhdWx0IikNCnBsb3QoZF9lcGFuZWNobmlrb3YsIG1haW4gPSAiRXBhbmVjaG5pa292IikNCnBsb3QoZF9yZWN0YW5ndWxhciwgbWFpbiA9ICJSZWN0YW5ndWxhciIpDQoNCmBgYA0KDQpaIHJvenLDs8W8bmllbmllbSBuYSBwxYJlxIc6DQoNCmBgYHtyfQ0KcGxvdF9nIDwtIGdncGxvdChkYW5lLCBhZXMoeD1kb2Nob2QsIGZpbGw9cGxlYykpKw0KICBzdGF0X2RlbnNpdHkoKSsNCiAgbGFicyh0aXRsZT0iRXN0eW1hY2phIGfEmXN0b8WbY2kgeiBqxIVkcmVtIEdhdXNzYSIpDQpwbG90X2cNCmBgYA0KDQpgYGB7cn0NCnBsb3RfZSA8LSBnZ3Bsb3QoZGFuZSwgYWVzKHg9ZG9jaG9kLCBmaWxsPXBsZWMpKSsNCiAgc3RhdF9kZW5zaXR5KGtlcm5lbCA9ICJlcGFuZWNobmlrb3YiKSsNCiAgbGFicyh0aXRsZT0iRXN0eW1hY2phIGfEmXN0b8WbY2kgeiBqxIVkcmVtIEVwYW5lY2huaWtvdmEiKQ0KcGxvdF9lDQpgYGANCg0KYGBge3J9DQpwbG90X3QgPC0gZ2dwbG90KGRhbmUsIGFlcyh4PWRvY2hvZCwgZmlsbD1wbGVjKSkrDQogIHN0YXRfZGVuc2l0eShrZXJuZWwgPSAicmVjdGFuZ3VsYXIiKSsNCiAgbGFicyh0aXRsZT0iRXN0eW1hY2phIGfEmXN0b8WbY2kgeiBqxIVkcmVtIHByb3N0b2vEhXRueW0iKQ0KcGxvdF90DQpgYGANCg0KKipXbmlvc2VrKio6IFLDs8W8bmUgdHlwdSBqxIVkcmEgZGFqxIUgcG9kb2JuZSB3eW5pa2ksIHphdGVtIGRvIGRhbHN6ZWoNCmFuYWxpenkgd3lzdGFyY3p5IHXFvHnEhyBqxIVkcmEgZG9tecWbbG5lZ28gLSBHYXVzb3dza2llZ28uDQoNCiMjIyMgU2VsZWtjamEgcGFzbWENCg0KYGBge3J9DQpkXzAgPC0gZGVuc2l0eShkYW5lJGRvY2hvZCwgYncgPSAibnJkMCIpDQpwbG90KGRfMCwgbWFpbiA9ICJQYXNtbyBucmQwIiwgY29sPSJ5ZWxsb3dncmVlbiIpDQoNCmRfc2NvdHQgPC0gZGVuc2l0eShkYW5lJGRvY2hvZCwgYncgPSAibnJkIikNCnBsb3QoZF9zY290dCwgbWFpbiA9ICJQYXNtbyBTY290dGEiLCBjb2w9J21pZG5pZ2h0Ymx1ZScpDQoNCmRfdWN2IDwtIGRlbnNpdHkoZGFuZSRkb2Nob2QsIGJ3ID0gInVjdiIpDQpwbG90KGRfdWN2LCBtYWluID0gIlBhc21vIFVDViIsIGNvbD0iY29yYWwiKQ0KDQpkX1NKIDwtIGRlbnNpdHkoZGFuZSRkb2Nob2QsIGJ3ID0gIlNKIikNCnBsb3QoZF9TSiwgbWFpbiA9ICJQYXNtbyBTaGVhdGhlcmEgJiBKb25lc2EiLCBjb2w9ImRhcmtjeWFuIikNCmBgYA0KDQoqKlduaW9zZWsqKjogU3plcm9rb8WbxIcgcGFzbWEgd3DFgnl3YSBuYSB3eW5pa2kgb3N6YWNvd2FuaWEgZ2VzdG/Fm2NpLg0KTWV0b2R5IFNKIGkgVUNWIG1hasSFIHpieXQgbWHFgsSFIHN6ZXJva2/Fm2MgcGFzbWEsIHphdGVtIHPEhSBuYWRtaWVybmllDQpkb3Bhc29wd3VqZSBzaWUgZG8ga3J6eXdlai4NCg0KT3B0eW1hbG55bSB3eWJvcmVtIG1vxbxlIGJ5xIcgW3JlZ3XFgmEgU2NvdHRhXXsudW5kZXJsaW5lfSBsdWINCltkb215xZtsbmFdey51bmRlcmxpbmV9Lg0KDQpgYGB7cn0NCmdncGxvdChkYW5lLCBhZXMoeD1kb2Nob2QsIGZpbGw9cGxlYykpKw0KICBzdGF0X2RlbnNpdHkoYncgPSAibnJkIikrDQogIGxhYnModGl0bGU9IkVzdHltYWNqYSBnxJlzdG/Fm2NpIHogcGFzbWVtIFNjb3R0YSB6IHBvZHppYcWCZW0gbmEgcMWCZcSHIikNCmBgYA0KDQojIyMgT3N6YWNvd2FuaWUgc2t1bXVsb3dhbmVqIGfEmXN0b8WbY2kNCg0KRHlzdHJ5YnVhbnRhIHRvIGZ1bmtjamEsIGt0w7NyYSBvcGlzdWplIHByYXdkb3BvZG9iaWXFhHN0d28sIMW8ZSB6bWllbm5hDQpsb3Nvd2EgcHJ6eWptaWUgd2FydG/Fm8SHIG1uaWVqc3rEhSBsdWIgcsOzd27EhSBkYW5laiB3YXJ0b8WbY2kgeC4NCg0KIyMjIyAqKlR5cCBqxIVkcmEqKg0KDQpgYGB7cn0NCmR5c3RyeWJ1YW50YV9nIDwtIGFwcHJveGZ1bihkX2dhdXNzaWFuJHgsDQogICAgICAgICAgICAgICAgICAgICAgICAgIGN1bXN1bShkX2dhdXNzaWFuJHkpL3N1bShkX2dhdXNzaWFuJHkpKQ0KDQpkeXN0cnlidWFudGFfZSA8LSBhcHByb3hmdW4oZF9lcGFuZWNobmlrb3YkeCwNCiAgICAgICAgICAgICAgICAgICAgICAgICAgY3Vtc3VtKGRfZXBhbmVjaG5pa292JHkpL3N1bShkX2VwYW5lY2huaWtvdiR5KSkNCg0KZHlzdHJ5YnVhbnRhX3IgPC0gYXBwcm94ZnVuKGRfcmVjdGFuZ3VsYXIkeCwNCiAgICAgICAgICAgICAgICAgICAgICAgICAgY3Vtc3VtKGRfcmVjdGFuZ3VsYXIkeSkvc3VtKGRfcmVjdGFuZ3VsYXIkeSkpDQoNCnhfdmFscyA8LSBzZXEobWluKGRhbmUkZG9jaG9kKSwgbWF4KGRhbmUkZG9jaG9kKSwgbGVuZ3RoLm91dCA9IDEwMCkNCmBgYA0KDQpgYGB7cn0NCg0KcGFyKG1mcm93ID0gYygzLCAxKSkNCnBsb3QoeF92YWxzLCBkeXN0cnlidWFudGFfZyh4X3ZhbHMpLCBwY2g9MSwNCiAgICAgbWFpbiA9ICJDREYgZGxhIGrEhWRyYSBHYXVzc293c2tpZWdvIiwgDQogICAgIHhsYWIgPSAiRG9jaMOzZCIsIHlsYWIgPSAiRHlzdHJ5YnVhbnRhIikNCnBsb3QoeF92YWxzLCBkeXN0cnlidWFudGFfZSh4X3ZhbHMpLCBwY2g9MSwNCiAgICAgbWFpbiA9ICJDREYgZGxhIGrEhWRyYSBFcGFuZWNobmlrb3ZhIiwgDQogICAgIHhsYWIgPSAiRG9jaMOzZCIsIHlsYWIgPSAiRHlzdHJ5YnVhbnRhIikNCnBsb3QoeF92YWxzLCBkeXN0cnlidWFudGFfcih4X3ZhbHMpLCBwY2g9MSwNCiAgICAgbWFpbiA9ICJDREYgZGxhIGrEhWRyYSBwcm9zdG9rxIV0bmVnbyIsIA0KICAgICB4bGFiID0gIkRvY2jDs2QiLCB5bGFiID0gIkR5c3RyeWJ1YW50YSIpDQpgYGANCg0KIyMjIyBTZWxla2NqYSBwYXNtYQ0KDQpgYGB7cn0NCmR5c3RyeWJ1YW50YV8wIDwtIGFwcHJveGZ1bihkXzAkeCwNCiAgICAgICAgICAgICAgICAgICAgICAgICAgY3Vtc3VtKGRfMCR5KS9zdW0oZF8wJHkpKQ0KDQpkeXN0cnlidWFudGFfcyA8LSBhcHByb3hmdW4oZF9zY290dCR4LA0KICAgICAgICAgICAgICAgICAgICAgICAgICBjdW1zdW0oZF9zY290dCR5KS9zdW0oZF9zY290dCR5KSkNCg0KZHlzdHJ5YnVhbnRhX3VjdiA8LSBhcHByb3hmdW4oZF91Y3YkeCwNCiAgICAgICAgICAgICAgICAgICAgICAgICAgY3Vtc3VtKGRfdWN2JHkpL3N1bShkX3VjdiR5KSkNCg0KZHlzdHJ5YnVhbnRhX1NKIDwtIGFwcHJveGZ1bihkX1NKJHgsDQogICAgICAgICAgICAgICAgICAgICAgICAgIGN1bXN1bShkX1NKJHkpL3N1bShkX1NKJHkpKQ0KDQp4X3ZhbHMgPC0gc2VxKG1pbihkYW5lJGRvY2hvZCksIG1heChkYW5lJGRvY2hvZCksIGxlbmd0aC5vdXQgPSAxMDApDQoNCmBgYA0KDQpgYGB7cn0NCg0KcGxvdCh4X3ZhbHMsIGR5c3RyeWJ1YW50YV8wKHhfdmFscyksIHBjaD0xLCANCiAgICAgbWFpbiA9ICJDREYgZGxhIHBhc21hIG5yZDAiLCANCiAgICAgeGxhYiA9ICJEb2Now7NkIiwgeWxhYiA9ICJEeXN0cnlidWFudGEiLCANCiAgICAgY29sID0gInllbGxvd2dyZWVuIiwgbHdkID0gMikNCg0KDQpwbG90KHhfdmFscywgZHlzdHJ5YnVhbnRhX3MoeF92YWxzKSwgcGNoPTEsIA0KICAgICBtYWluID0gIkNERiBkbGEgcGFzbWEgbnJkMCIsIA0KICAgICB4bGFiID0gIkRvY2jDs2QiLCB5bGFiID0gIkR5c3RyeWJ1YW50YSIsIA0KICAgICBjb2wgPSAibWlkbmlnaHRibHVlIiwgbHdkID0gMikNCg0KDQpwbG90KHhfdmFscywgZHlzdHJ5YnVhbnRhX3Vjdih4X3ZhbHMpLCBwY2g9MSwgDQogICAgIG1haW4gPSAiQ0RGIGRsYSBwYXNtYSBucmQwIiwgDQogICAgIHhsYWIgPSAiRG9jaMOzZCIsIHlsYWIgPSAiRHlzdHJ5YnVhbnRhIiwgDQogICAgIGNvbCA9ICJjb3JhbCIsIGx3ZCA9IDIpDQoNCg0KcGxvdCh4X3ZhbHMsIGR5c3RyeWJ1YW50YV9TSih4X3ZhbHMpLCBwY2g9MSwgDQogICAgIG1haW4gPSAiQ0RGIGRsYSBwYXNtYSBucmQwIiwgDQogICAgIHhsYWIgPSAiRG9jaMOzZCIsIHlsYWIgPSAiRHlzdHJ5YnVhbnRhIiwgDQogICAgIGNvbCA9ICJkYXJrY3lhbiIsIGx3ZCA9IDIpDQpgYGANCg0KKipXbmlvc2VrKio6IFN6ZXJva2/Fm8SHIHBhc21hIHpuaWtvbW8gd3DFgnl3YSBuYSB3eW5pa2kgb3N6YWNvd2FuaWENCmR5c3RyeWJ1YW50eS4NCg0KRXN0eW1hY2phIGfEmXN0b8WbY2kgaSBza3VtdWxvd2FuZWogZ8SZc3RvxZtjaSBzxIUgcG90xJnFvG55bWkgbmFyesSZZHppYW1pIGRvDQphbmFsaXp5IGRhbnljaC4gUsOzxbxuZSB0eXB5IGrEhWRlciBpIG1ldG9keSBkb2JvcnUgcGFzbWEgbW9nxIUgcHJvd2FkemnEhyBkbw0KcsOzxbxueWNoIHJlenVsdGF0w7N3LCBjbyBwb2RrcmXFm2xhIHpuYWN6ZW5pZSBzdGFyYW5uZWdvIHd5Ym9ydSBtZXRvZA0KYW5hbGl6eSB3IGJhZGFuaWFjaCBzdGF0eXN0eWN6bnljaC4gTmF0b21pYXN0IGFuYWxpem93YW5lIGRhbmUgbWFqxIUNCndhcnRvxZtjaSBvZHN0YWrEhWNlLCBrdMOzcmUgem5hY3puaWUgd3DFgnluxJnFgnkgbmEgYW5hbGl6xJkgZ8SZc3RvxZtjaSBpDQpkeXN0cnlidWFudHkuIFNwb3dvZG93YcWCeSBvbmUsIMW8ZSByw7PFvG5pY2UgcG9tacSZZHp5IHLDs8W8bnltaSBwYXNtYW1pIGN6eQ0KasSFZHJhbWksIG5pZSB3cMWCeXdhamEgaXN0b25pZSBuYSBhbmFsaXrEmSAoIHogd3lqxIV0a2llbSBkb2JvcnUgcGFzbWEgZGxhDQpnxJlzdG/Fm2NpICkuDQo=