This is the final analysis. All the datasets have been pre-processing
into the df_filtered.rds file
EDA
Hoy many patients?
n_distinct(df_filtered$pid) %>%
knitr::kable()
How many interventions?
df_filtered %>%
select(ep_beig_dat, manipulation_type, periods) %>%
# remove first semester 2020
filter(!between(ep_beig_dat, as.Date('2020-06-30'), as.Date('2020-12-31'))) %>%
# remove first semester 2021
filter(!between(ep_beig_dat, as.Date('2021-06-30'), as.Date('2021-12-31'))) %>%
# count
select(-ep_beig_dat) %>%
mutate(manipulation_type = fct_drop(manipulation_type)) %>%
group_by(manipulation_type, periods) %>%
count() %>%
pivot_wider(
names_from = periods,
,
names_prefix = "y",
values_from = n
) %>%
mutate("Variation 2020" = (y2020 - y2019) / y2019 * 100) %>%
mutate("Variation 2021" = (y2021 - y2019) / y2019 * 100) %>%
knitr::kable()
Dental hygiene |
88729 |
62588 |
80901 |
-29.46162 |
-8.822369 |
Examination |
52853 |
38395 |
51622 |
-27.35512 |
-2.329102 |
Fluoride applications |
61618 |
45085 |
58352 |
-26.83145 |
-5.300399 |
Hygiene instructions |
62224 |
45382 |
58933 |
-27.06673 |
-5.288956 |
NA

df_filtered %>%
# remove first semester 2020
filter(!between(ep_beig_dat, as.Date('2020-06-30'), as.Date('2020-12-31'))) %>%
# remove first semester 2021
filter(!between(ep_beig_dat, as.Date('2021-06-30'), as.Date('2021-12-31'))) %>%
# mutate(manipulation_type = fct_lump_prop(manipulation_type, prop = .001)) %>%
# mutate(manipulation_type = replace_na(manipulation_type, "Other")) %>%
filter(!is.na(manipulation_type)) %>%
group_by(manipulation_type, periods) %>%
count() %>%
ggplot(aes(x = as.factor(periods),
y = n,
color = manipulation_type,
group = manipulation_type)) +
geom_line() +
scale_y_log10(labels = scales::label_number(scale_cut = scales::cut_short_scale())) +
labs(title = "Manipulations per year (first semester)",
x = "Year",
y = "N (x1000)",
color = "Manipulation")

How many specialties per year
Filter according to https://docs.google.com/document/d/17c5QXkbnCI9aEFDIblwdOLP-zfS5e9NFxVn5TjOTXEE/edit#heading=h.nmf14n
P25 |
General dentist |
P26 |
Maxillofacial surgeon |
|
|
P32 |
radiologist |
A253 |
Paediatric dentist |
A251 |
orthodontist |
n11 |
Dental hygienist |
df_filtered %>%
filter(spec_kods %in% c("P25", "P26", "P32", "A253", "A251", "n11")) %>%
group_by(periods, spec_kods) %>%
count() %>%
pivot_wider(names_from = periods,
values_from = n) %>%
knitr::kable()
n11 |
264889 |
465554 |
507680 |
P26 |
534 |
59 |
NA |
P32 |
1 |
NA |
NA |
Manipulation per date
Check the dates
df_filtered %>%
# remove first semester 2020
filter(!between(ep_beig_dat, as.Date('2020-06-30'), as.Date('2020-12-31'))) %>%
# remove first semester 2021
filter(!between(ep_beig_dat, as.Date('2021-06-30'), as.Date('2021-12-31'))) %>%
# group_by(year, month, day, day_week) %>%
# count() %>%
group_by(month = lubridate::floor_date(ep_beig_dat, unit = "month")) %>%
count() %>%
mutate(month = lubridate::ymd(month)) %>%
ggplot(aes(x = month,
y = n,
group = 1)) +
geom_point() +
geom_line() +
scale_y_log10(labels = scales::label_number(scale_cut = scales::cut_short_scale())) +
scale_x_date(NULL, date_labels = "%b %y", breaks = "month",
) +
# scale_x_date(limits = as.Date(c("2019-01-01", "2021-12-31"))) +
theme(axis.text.x = element_text(size = 8, angle = 45, colour = "black",
vjust = 1, hjust = 1)) +
labs(title = "Manipulations per day, 2019-2021",
y = "Manipulations (log 10)",
x = "Date")

ggsave(here("Figs2019_2021", "fig1.tif"), width = 6, height = 4, device='tiff', dpi=300)
Manipulations
df_filtered %>%
select(ep_beig_dat, manipulation_type, periods) %>%
# remove first semester 2020
filter(!between(ep_beig_dat, as.Date('2020-06-30'), as.Date('2020-12-31'))) %>%
# remove first semester 2021
filter(!between(ep_beig_dat, as.Date('2021-06-30'), as.Date('2021-12-31'))) %>%
# count
group_by(manipulation_type, periods) %>%
count() %>%
mutate(error_estimate = sqrt(n)) %>%
# create the graph
ggplot(aes(
x = as.factor(periods),
y = n,
fill = manipulation_type
)) +
geom_col(position="dodge") + # the position="dodge" allow to have the bars by side
# scale_fill_manual(values = c("#C2C1C1", "#89272F")) +
scale_fill_viridis_d() +
# scale_fill_manual(values = c("grey90", "grey60", "grey30", "grey10")) +
# scale_y_log10(labels = scales::label_number()) +
labs(
# title = "Total of manipulations during the first semester",
x = "Year (First Semester)",
y = "Manipulations",
fill = ""
) +
theme(legend.position="top") +
geom_errorbar(
aes(
ymin = n - error_estimate * 4,
ymax = n + error_estimate * 4
),
width = .2,
position = position_dodge(.9)
)

ggsave(here("Figs2019_2021", "fig2.tif"), width = 7, height = 4, device='tiff', dpi=300)
Manipulations per day
df_filtered %>%
mutate(ep_beig_dat = lubridate::ymd(ep_beig_dat)) %>%
group_by(ep_beig_dat, manipulation_type) %>% # add kodes_grouped to see the kodes
count() %>%
# so far, here are the manipulations per day
# count() %>% # here is the number of manipulacijas per day
# add the name of the day
mutate(day = lubridate::wday(
lubridate::ymd(ep_beig_dat),
label = TRUE,
abbr = TRUE
)) %>%
ggplot(aes(x = ep_beig_dat,
y = n,
color = day)) +
geom_point() +
labs(
title = "Manipulations per day of the week",
y = "Manipulations (n)",
x = "Date",
color = "Day of the week"
) +
scale_fill_viridis_b() +
theme(legend.position="top")

ggsave(here("Figs2019_2021", "fig3.tif"), width = 7, height = 4, device='tiff', dpi=300)
Manipulations per type
df_filtered %>%
mutate(ep_beig_dat = lubridate::ymd(ep_beig_dat)) %>%
group_by(ep_beig_dat, manipulation_type) %>% # add kodes_grouped to see the kodes
count() %>%
# so far, here are the manipulations per day
# count() %>% # here is the number of manipulacijas per day
# add the name of the day
mutate(day = lubridate::wday(
lubridate::ymd(ep_beig_dat),
label = TRUE,
abbr = TRUE
)) %>%
ggplot(aes(x = ep_beig_dat,
y = n,
color = day)) +
geom_point() +
labs(
title = "Manipulations per day of the week",
y = "Manipulations n",
x = "Date",
color = "Day of the week"
) +
# scale_y_log10() +
scale_fill_viridis_b() +
facet_grid(manipulation_type ~ . ) +
theme(legend.position = "top") +
theme(strip.text.y = element_text(size = 8))

ggsave(here("Figs2019_2021", "fig4.tif"), width = 8, height = 6, device='tiff', dpi=300)
LS0tCnRpdGxlOiAiQ09WSUQgTGF0dmlhIDIwMTkgdGlsIDIwMjAiCm91dHB1dDogCiAgaHRtbF9ub3RlYm9vazogCiAgICB0b2M6IHllcwogICAgdG9jX2Zsb2F0OiB0cnVlCiAgICBmaWdfY2FwdGlvbjogdHJ1ZQogICAgY29kZV9mb2xkaW5nOiBoaWRlCi0tLQoKYGBge3J9CmtuaXRyOjpvcHRzX2NodW5rJHNldChlY2hvID0gVFJVRSwgd2FybmluZz1GQUxTRSkKYGBgCgpUaGlzIGlzIHRoZSBmaW5hbCBhbmFseXNpcy4gQWxsIHRoZSBkYXRhc2V0cyBoYXZlIGJlZW4gcHJlLXByb2Nlc3NpbmcgaW50byB0aGUgZGZfZmlsdGVyZWQucmRzIGZpbGUKCiMgUGFja2FnZXMKCmBgYHtyfQpwYWNtYW46OnBfbG9hZCh0aWR5dmVyc2UsICMgZGF0YSBzY2llbmNlIHRvb2xzCiAgICAgICAgICAgICAgIGphbml0b3IsICMgZGF0YSBjbGVhbmluZyBhbmQgdGFieWwKICAgICAgICAgICAgICAgc2YsICAjIGZvciBtYXBzCiAgICAgICAgICAgICAgIGd0c3VtbWFyeSwgICMgZm9yIHRhYmxlcyBhbmQgcmVncmVzc2lvbiBzdW1tYXJ5CiAgICAgICAgICAgICAgIGdncHViciwgIyBmb3IgZ2dwbG90IHRoZW1lcwogICAgICAgICAgICAgICBzY2FsZXMsICMgZm9yIGdncGxvdCBzY2FsZXMKICAgICAgICAgICAgICAgaGVyZSkgIyBmaWxlcyBwYXRocwpgYGAKCmBgYHtyfQp0aGVtZV9zZXQodGhlbWVfbWluaW1hbCgpKQpgYGAKCiMgMi4gU1RBUlQgRlJPTSBIRVJFIExvYWQgdGhlIFJEUyBmaWxlCgpgYGB7cn0KIyBkZiA8LSByZWFkUkRTKGhlcmUoImRhdGFzZXRzIiwgImRmLnJkcyIpKQojIHRlc3Qgd2l0aCBuZXcgZGF0YXNldAojIGRmIDwtIHJlYWRSRFMoaGVyZSgiZGF0YXNldHMiLCAiZGZfd2l0aF9hbGxfMjAyMS5yZHMiKSkKZGZfZmlsdGVyZWQgPC0gcmVhZFJEUyhoZXJlKCJkYXRhc2V0cyIsICJkZl9maWx0ZXJlZC5yZHMiKSkKCmBgYAoKIyMgRmlsdGVyIGRhdGVzIHRvIGF2b2lkIGRhdGVzIGZyb20gdGhlIHNlY29uZCBzZW1lc3RlciAyMDE5CgpgYGB7cn0KZGZfZmlsdGVyZWQgPC0gZGZfZmlsdGVyZWQgJT4lCiAgZmlsdGVyKGVwX2JlaWdfZGF0ID4gIjIwMTgtMTItMzEiKSAlPiUgCiAgZmlsdGVyKCFiZXR3ZWVuKGVwX2JlaWdfZGF0LCBhcy5EYXRlKCcyMDE5LTA2LTMwJyksIGFzLkRhdGUoJzIwMTktMTItMzEnKSkpCgpgYGAKCiMjIyMgQ29kaWZpY2F0aW9uCgojIEVEQQoKSG95IG1hbnkgcGF0aWVudHM/CgpgYGB7cn0Kbl9kaXN0aW5jdChkZl9maWx0ZXJlZCRwaWQpICU+JSAKICBrbml0cjo6a2FibGUoKQpgYGAKCkhvdyBtYW55IGludGVydmVudGlvbnM/CgpgYGB7cn0KCmRmX2ZpbHRlcmVkICU+JQogIHNlbGVjdChlcF9iZWlnX2RhdCwgbWFuaXB1bGF0aW9uX3R5cGUsIHBlcmlvZHMpICU+JQogICMgcmVtb3ZlIGZpcnN0IHNlbWVzdGVyIDIwMjAKICBmaWx0ZXIoIWJldHdlZW4oZXBfYmVpZ19kYXQsIGFzLkRhdGUoJzIwMjAtMDYtMzAnKSwgYXMuRGF0ZSgnMjAyMC0xMi0zMScpKSkgJT4lCiAgIyByZW1vdmUgZmlyc3Qgc2VtZXN0ZXIgMjAyMQogIGZpbHRlcighYmV0d2VlbihlcF9iZWlnX2RhdCwgYXMuRGF0ZSgnMjAyMS0wNi0zMCcpLCBhcy5EYXRlKCcyMDIxLTEyLTMxJykpKSAlPiUKICAjIGNvdW50CiAgc2VsZWN0KC1lcF9iZWlnX2RhdCkgJT4lCiAgbXV0YXRlKG1hbmlwdWxhdGlvbl90eXBlID0gZmN0X2Ryb3AobWFuaXB1bGF0aW9uX3R5cGUpKSAlPiUKICBncm91cF9ieShtYW5pcHVsYXRpb25fdHlwZSwgcGVyaW9kcykgJT4lCiAgY291bnQoKSAlPiUKICBwaXZvdF93aWRlcigKICAgIG5hbWVzX2Zyb20gPSBwZXJpb2RzLAogICAgLAogICAgbmFtZXNfcHJlZml4ID0gInkiLAogICAgdmFsdWVzX2Zyb20gPSBuCiAgKSAlPiUKICBtdXRhdGUoIlZhcmlhdGlvbiAyMDIwIiA9ICh5MjAyMCAtIHkyMDE5KSAvIHkyMDE5ICogMTAwKSAlPiUgCiAgbXV0YXRlKCJWYXJpYXRpb24gMjAyMSIgPSAoeTIwMjEgLSB5MjAxOSkgLyB5MjAxOSAqIDEwMCkgJT4lIAogIGtuaXRyOjprYWJsZSgpCgpgYGAKCmBgYHtyfQpkZl9maWx0ZXJlZCAlPiUKICBzZWxlY3QoZXBfYmVpZ19kYXQsIG1hbmlwdWxhdGlvbl90eXBlLCBwZXJpb2RzKSAlPiUKICAjIHJlbW92ZSBmaXJzdCBzZW1lc3RlciAyMDIwCiAgZmlsdGVyKCFiZXR3ZWVuKGVwX2JlaWdfZGF0LCBhcy5EYXRlKCcyMDIwLTA2LTMwJyksIGFzLkRhdGUoJzIwMjAtMTItMzEnKSkpICU+JQogICMgcmVtb3ZlIGZpcnN0IHNlbWVzdGVyIDIwMjEKICBmaWx0ZXIoIWJldHdlZW4oZXBfYmVpZ19kYXQsIGFzLkRhdGUoJzIwMjEtMDYtMzAnKSwgYXMuRGF0ZSgnMjAyMS0xMi0zMScpKSkgJT4lCiAgIyBjb3VudAogIHNlbGVjdCgtZXBfYmVpZ19kYXQpICU+JQogIG11dGF0ZShtYW5pcHVsYXRpb25fdHlwZSA9IGZjdF9kcm9wKG1hbmlwdWxhdGlvbl90eXBlKSkgJT4lCiAgZ3JvdXBfYnkobWFuaXB1bGF0aW9uX3R5cGUsIHBlcmlvZHMpICU+JQogIGNvdW50KCkgJT4lCiAgcGl2b3Rfd2lkZXIoCiAgICBuYW1lc19mcm9tID0gcGVyaW9kcywKICAgICwKICAgIG5hbWVzX3ByZWZpeCA9ICJ5IiwKICAgIHZhbHVlc19mcm9tID0gbgogICkgJT4lCiAgbXV0YXRlKCJWYXJpYXRpb25fMjAyMCIgPSAoeTIwMjAgLSB5MjAxOSkgLyB5MjAxOSAqIDEwMCkgJT4lIAogIG11dGF0ZSgiVmFyaWF0aW9uXzIwMjEiID0gKHkyMDIxIC0geTIwMTkpIC8geTIwMTkgKiAxMDApICU+JSAKICBzZWxlY3QobWFuaXB1bGF0aW9uX3R5cGUsIFZhcmlhdGlvbl8yMDIwLCBWYXJpYXRpb25fMjAyMSApICU+JSAKICBwaXZvdF9sb25nZXIoVmFyaWF0aW9uXzIwMjA6VmFyaWF0aW9uXzIwMjEsIAogICAgICAgICAgICAgICBuYW1lc190byA9ICJQZXJpb2QiLCAKICAgICAgICAgICAgICAgdmFsdWVzX3RvID0gIm4iKSAlPiUgCiAgZ2dwbG90KGFlcyh4ID0gUGVyaW9kLCAKICAgICAgICAgICAgIHkgPSBuLCAKICAgICAgICAgICAgIGZpbGwgPSBtYW5pcHVsYXRpb25fdHlwZSkpICsgCiAgIGdlb21fY29sKHBvc2l0aW9uPSJkb2RnZSIpICsgIyB0aGUgcG9zaXRpb249ImRvZGdlIiBhbGxvdyB0byBoYXZlIHRoZSBiYXJzIGJ5IHNpZGUKICAjIHNjYWxlX2ZpbGxfbWFudWFsKHZhbHVlcyA9IGMoIiNDMkMxQzEiLCAiIzg5MjcyRiIpKSArCiAgc2NhbGVfZmlsbF92aXJpZGlzX2QoKSAgKyAKICBsYWJzKHRpdGxlID0gIkNvbXBhcmlzb24gdG8gMjAxOSIsIAogICAgICAgZmlsbCA9ICJNYW5pcHVsYXRpb25zIiwgCiAgICAgICB5ID0gIlBlcmNlbnRhZ2UgQ2hhbmdlIikrCiAgdGhlbWUobGVnZW5kLnBvc2l0aW9uID0gInRvcCIpCiAgCmBgYAoKYGBge3J9CmRmX2ZpbHRlcmVkICU+JSAKICAgICMgcmVtb3ZlIGZpcnN0IHNlbWVzdGVyIDIwMjAKICBmaWx0ZXIoIWJldHdlZW4oZXBfYmVpZ19kYXQsIGFzLkRhdGUoJzIwMjAtMDYtMzAnKSwgYXMuRGF0ZSgnMjAyMC0xMi0zMScpKSkgJT4lCiAgIyByZW1vdmUgZmlyc3Qgc2VtZXN0ZXIgMjAyMQogIGZpbHRlcighYmV0d2VlbihlcF9iZWlnX2RhdCwgYXMuRGF0ZSgnMjAyMS0wNi0zMCcpLCBhcy5EYXRlKCcyMDIxLTEyLTMxJykpKSAlPiUKICAjIG11dGF0ZShtYW5pcHVsYXRpb25fdHlwZSA9IGZjdF9sdW1wX3Byb3AobWFuaXB1bGF0aW9uX3R5cGUsIHByb3AgPSAuMDAxKSkgJT4lIAogICMgbXV0YXRlKG1hbmlwdWxhdGlvbl90eXBlID0gcmVwbGFjZV9uYShtYW5pcHVsYXRpb25fdHlwZSwgIk90aGVyIikpICU+JSAKICBmaWx0ZXIoIWlzLm5hKG1hbmlwdWxhdGlvbl90eXBlKSkgJT4lIAogIGdyb3VwX2J5KG1hbmlwdWxhdGlvbl90eXBlLCBwZXJpb2RzKSAlPiUgCiAgY291bnQoKSAlPiUgCiAgZ2dwbG90KGFlcyh4ID0gYXMuZmFjdG9yKHBlcmlvZHMpLCAKICAgICAgICAgICAgIHkgPSBuLCAKICAgICAgICAgICAgIGNvbG9yID0gbWFuaXB1bGF0aW9uX3R5cGUsIAogICAgICAgICAgICAgZ3JvdXAgPSBtYW5pcHVsYXRpb25fdHlwZSkpICsKICBnZW9tX2xpbmUoKSArCiAgc2NhbGVfeV9sb2cxMChsYWJlbHMgPSBzY2FsZXM6OmxhYmVsX251bWJlcihzY2FsZV9jdXQgPSBzY2FsZXM6OmN1dF9zaG9ydF9zY2FsZSgpKSkgKwogIGxhYnModGl0bGUgPSAiTWFuaXB1bGF0aW9ucyBwZXIgeWVhciAoZmlyc3Qgc2VtZXN0ZXIpIiwgCiAgICAgICB4ID0gIlllYXIiLCAKICAgICAgIHkgPSAiTiAoeDEwMDApIiwgCiAgICAgICBjb2xvciA9ICJNYW5pcHVsYXRpb24iKQpgYGAKCkhvdyBtYW55IHNwZWNpYWx0aWVzIHBlciB5ZWFyCgpGaWx0ZXIgYWNjb3JkaW5nIHRvIDxodHRwczovL2RvY3MuZ29vZ2xlLmNvbS9kb2N1bWVudC9kLzE3YzVRWGtibkNJOWFFRkRJYmx3ZE9MUC16ZlM1ZTlORnhWbjVUak9UWEVFL2VkaXQjaGVhZGluZz1oLm5tZjE0bj4KCnwgQ29kZXMgfCBFeHBsaWNhdGlvbiAgICAgICAgICAgfAp8LS0tLS0tLXwtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLXwKfCBQMjUgICB8IEdlbmVyYWwgZGVudGlzdCAgICAgICB8CnwgUDI2ICAgfCBNYXhpbGxvZmFjaWFsIHN1cmdlb24gfAp8ICAgICAgIHwgICAgICAgICAgICAgICAgICAgICAgIHwKfCBQMzIgICB8IHJhZGlvbG9naXN0ICAgICAgICAgICB8CnwgQTI1MyAgfCBQYWVkaWF0cmljIGRlbnRpc3QgICAgfAp8IEEyNTEgIHwgb3J0aG9kb250aXN0ICAgICAgICAgIHwKfCBuMTEgICB8IERlbnRhbCBoeWdpZW5pc3QgICAgICB8CgpgYGB7cn0KZGZfZmlsdGVyZWQgJT4lIAogIGZpbHRlcihzcGVjX2tvZHMgJWluJSBjKCJQMjUiLCAiUDI2IiwgIlAzMiIsICJBMjUzIiwgIkEyNTEiLCAibjExIikpICU+JSAKICBncm91cF9ieShwZXJpb2RzLCBzcGVjX2tvZHMpICU+JSAKICBjb3VudCgpICU+JSAKICBwaXZvdF93aWRlcihuYW1lc19mcm9tID0gcGVyaW9kcywgCiAgICAgICAgICAgICAgdmFsdWVzX2Zyb20gPSBuKSAlPiUgCiAga25pdHI6OmthYmxlKCkKYGBgCgojIyBNYW5pcHVsYXRpb24gcGVyIGRhdGUKCkNoZWNrIHRoZSBkYXRlcwoKYGBge3J9CmRmX2ZpbHRlcmVkICU+JQogICMgcmVtb3ZlIGZpcnN0IHNlbWVzdGVyIDIwMjAKICBmaWx0ZXIoIWJldHdlZW4oZXBfYmVpZ19kYXQsIGFzLkRhdGUoJzIwMjAtMDYtMzAnKSwgYXMuRGF0ZSgnMjAyMC0xMi0zMScpKSkgJT4lCiAgIyByZW1vdmUgZmlyc3Qgc2VtZXN0ZXIgMjAyMQogIGZpbHRlcighYmV0d2VlbihlcF9iZWlnX2RhdCwgYXMuRGF0ZSgnMjAyMS0wNi0zMCcpLCBhcy5EYXRlKCcyMDIxLTEyLTMxJykpKSAlPiUKICAjIGdyb3VwX2J5KHllYXIsIG1vbnRoLCBkYXksIGRheV93ZWVrKSAlPiUKICAjIGNvdW50KCkgJT4lCiAgZ3JvdXBfYnkobW9udGggPSBsdWJyaWRhdGU6OmZsb29yX2RhdGUoZXBfYmVpZ19kYXQsIHVuaXQgPSAibW9udGgiKSkgJT4lCiAgY291bnQoKSAlPiUKICBtdXRhdGUobW9udGggPSBsdWJyaWRhdGU6OnltZChtb250aCkpICU+JQogIAogIGdncGxvdChhZXMoeCA9IG1vbnRoLAogICAgICAgICAgICAgeSA9IG4sCiAgICAgICAgICAgICBncm91cCA9IDEpKSArCiAgZ2VvbV9wb2ludCgpICsKICBnZW9tX2xpbmUoKSArCiAgc2NhbGVfeV9sb2cxMChsYWJlbHMgPSBzY2FsZXM6OmxhYmVsX251bWJlcihzY2FsZV9jdXQgPSBzY2FsZXM6OmN1dF9zaG9ydF9zY2FsZSgpKSkgKwogIHNjYWxlX3hfZGF0ZShOVUxMLCBkYXRlX2xhYmVscyA9ICIlYiAleSIsIGJyZWFrcyA9ICJtb250aCIsIAogICAgICAgICAgICAgICApICsKICAjIHNjYWxlX3hfZGF0ZShsaW1pdHMgPSBhcy5EYXRlKGMoIjIwMTktMDEtMDEiLCAiMjAyMS0xMi0zMSIpKSkgKwogIHRoZW1lKGF4aXMudGV4dC54ICA9IGVsZW1lbnRfdGV4dChzaXplID0gOCwgYW5nbGUgPSA0NSwgY29sb3VyID0gImJsYWNrIiwKICAgICAgdmp1c3QgPSAxLCBoanVzdCA9IDEpKSArIAogIGxhYnModGl0bGUgPSAiTWFuaXB1bGF0aW9ucyBwZXIgZGF5LCAyMDE5LTIwMjEiLAogICAgICAgeSA9ICJNYW5pcHVsYXRpb25zIChsb2cgMTApIiwKICAgICAgIHggPSAiRGF0ZSIpCmBgYAoKYGBge3J9Cmdnc2F2ZShoZXJlKCJGaWdzMjAxOV8yMDIxIiwgImZpZzEudGlmIiksIHdpZHRoID0gNiwgaGVpZ2h0ID0gNCwgZGV2aWNlPSd0aWZmJywgZHBpPTMwMCkKYGBgCgojIyBNYW5pcHVsYXRpb25zCgpgYGB7cn0KZGZfZmlsdGVyZWQgJT4lCiAgc2VsZWN0KGVwX2JlaWdfZGF0LCBtYW5pcHVsYXRpb25fdHlwZSwgcGVyaW9kcykgJT4lIAogICMgcmVtb3ZlIGZpcnN0IHNlbWVzdGVyIDIwMjAKICBmaWx0ZXIoIWJldHdlZW4oZXBfYmVpZ19kYXQsIGFzLkRhdGUoJzIwMjAtMDYtMzAnKSwgYXMuRGF0ZSgnMjAyMC0xMi0zMScpKSkgJT4lIAogICMgcmVtb3ZlIGZpcnN0IHNlbWVzdGVyIDIwMjEKIGZpbHRlcighYmV0d2VlbihlcF9iZWlnX2RhdCwgYXMuRGF0ZSgnMjAyMS0wNi0zMCcpLCBhcy5EYXRlKCcyMDIxLTEyLTMxJykpKSAlPiUgCiAgIyBjb3VudAogIGdyb3VwX2J5KG1hbmlwdWxhdGlvbl90eXBlLCBwZXJpb2RzKSAlPiUgCiAgY291bnQoKSAlPiUKICBtdXRhdGUoZXJyb3JfZXN0aW1hdGUgPSBzcXJ0KG4pKSAlPiUgCiAgIyBjcmVhdGUgdGhlIGdyYXBoCiAgZ2dwbG90KGFlcygKICAgIHggPSBhcy5mYWN0b3IocGVyaW9kcyksIAogICAgeSA9IG4sIAogICAgZmlsbCA9IG1hbmlwdWxhdGlvbl90eXBlCiAgICApKSArCiAgIGdlb21fY29sKHBvc2l0aW9uPSJkb2RnZSIpICsgIyB0aGUgcG9zaXRpb249ImRvZGdlIiBhbGxvdyB0byBoYXZlIHRoZSBiYXJzIGJ5IHNpZGUKICAjIHNjYWxlX2ZpbGxfbWFudWFsKHZhbHVlcyA9IGMoIiNDMkMxQzEiLCAiIzg5MjcyRiIpKSArCiAgc2NhbGVfZmlsbF92aXJpZGlzX2QoKSArCiAgIyBzY2FsZV9maWxsX21hbnVhbCh2YWx1ZXMgPSBjKCJncmV5OTAiLCAiZ3JleTYwIiwgImdyZXkzMCIsICJncmV5MTAiKSkgKwogICMgc2NhbGVfeV9sb2cxMChsYWJlbHMgPSBzY2FsZXM6OmxhYmVsX251bWJlcigpKSArCiAgICBsYWJzKAogICAgICAjIHRpdGxlID0gIlRvdGFsIG9mIG1hbmlwdWxhdGlvbnMgZHVyaW5nIHRoZSBmaXJzdCBzZW1lc3RlciIsIAogICAgICB4ID0gIlllYXIgKEZpcnN0IFNlbWVzdGVyKSIsIAogICAgICB5ID0gIk1hbmlwdWxhdGlvbnMiLCAKICAgICAgZmlsbCA9ICIiCiAgICApICArCiAgdGhlbWUobGVnZW5kLnBvc2l0aW9uPSJ0b3AiKSArIAogIGdlb21fZXJyb3JiYXIoCiAgICBhZXMoCiAgICAgIHltaW4gPSBuIC0gZXJyb3JfZXN0aW1hdGUgKiA0LAogICAgICB5bWF4ID0gbiArIGVycm9yX2VzdGltYXRlICogNAogICAgKSwKICAgIHdpZHRoID0gLjIsCiAgICBwb3NpdGlvbiA9IHBvc2l0aW9uX2RvZGdlKC45KQogICkgCmBgYAoKYGBge3J9Cmdnc2F2ZShoZXJlKCJGaWdzMjAxOV8yMDIxIiwgImZpZzIudGlmIiksIHdpZHRoID0gNywgaGVpZ2h0ID0gNCwgZGV2aWNlPSd0aWZmJywgZHBpPTMwMCkKYGBgCgojIyBNYW5pcHVsYXRpb25zIHBlciBkYXkKCmBgYHtyfQpkZl9maWx0ZXJlZCAlPiUKICBtdXRhdGUoZXBfYmVpZ19kYXQgPSBsdWJyaWRhdGU6OnltZChlcF9iZWlnX2RhdCkpICU+JQogIGdyb3VwX2J5KGVwX2JlaWdfZGF0LCBtYW5pcHVsYXRpb25fdHlwZSkgJT4lICMgYWRkIGtvZGVzX2dyb3VwZWQgdG8gc2VlIHRoZSBrb2RlcwogIGNvdW50KCkgJT4lCiAgIyBzbyBmYXIsIGhlcmUgYXJlIHRoZSBtYW5pcHVsYXRpb25zIHBlciBkYXkKICAjIGNvdW50KCkgJT4lICAgIyBoZXJlIGlzIHRoZSBudW1iZXIgb2YgbWFuaXB1bGFjaWphcyBwZXIgZGF5CiAgIyBhZGQgdGhlIG5hbWUgb2YgdGhlIGRheQogIG11dGF0ZShkYXkgPSBsdWJyaWRhdGU6OndkYXkoCiAgICBsdWJyaWRhdGU6OnltZChlcF9iZWlnX2RhdCksCiAgICBsYWJlbCA9IFRSVUUsCiAgICBhYmJyID0gVFJVRQogICkpICU+JQogIGdncGxvdChhZXMoeCA9IGVwX2JlaWdfZGF0LAogICAgICAgICAgICAgeSA9IG4sCiAgICAgICAgICAgICBjb2xvciA9IGRheSkpICsKICBnZW9tX3BvaW50KCkgKwogIGxhYnMoCiAgICB0aXRsZSA9ICJNYW5pcHVsYXRpb25zIHBlciBkYXkgb2YgdGhlIHdlZWsiLAogICAgeSA9ICJNYW5pcHVsYXRpb25zIChuKSIsCiAgICB4ID0gIkRhdGUiLAogICAgY29sb3IgPSAiRGF5IG9mIHRoZSB3ZWVrIgogICkgKwogIHNjYWxlX2ZpbGxfdmlyaWRpc19iKCkgKwogIHRoZW1lKGxlZ2VuZC5wb3NpdGlvbj0idG9wIikKYGBgCgpgYGB7cn0KZ2dzYXZlKGhlcmUoIkZpZ3MyMDE5XzIwMjEiLCAiZmlnMy50aWYiKSwgd2lkdGggPSA3LCBoZWlnaHQgPSA0LCBkZXZpY2U9J3RpZmYnLCBkcGk9MzAwKQpgYGAKCiMjIE1hbmlwdWxhdGlvbnMgcGVyIHR5cGUKCmBgYHtyfQpkZl9maWx0ZXJlZCAlPiUKICBtdXRhdGUoZXBfYmVpZ19kYXQgPSBsdWJyaWRhdGU6OnltZChlcF9iZWlnX2RhdCkpICU+JQogIGdyb3VwX2J5KGVwX2JlaWdfZGF0LCBtYW5pcHVsYXRpb25fdHlwZSkgJT4lICMgYWRkIGtvZGVzX2dyb3VwZWQgdG8gc2VlIHRoZSBrb2RlcwogIGNvdW50KCkgJT4lCiAgIyBzbyBmYXIsIGhlcmUgYXJlIHRoZSBtYW5pcHVsYXRpb25zIHBlciBkYXkKICAjIGNvdW50KCkgJT4lICAgIyBoZXJlIGlzIHRoZSBudW1iZXIgb2YgbWFuaXB1bGFjaWphcyBwZXIgZGF5CiAgIyBhZGQgdGhlIG5hbWUgb2YgdGhlIGRheQogIG11dGF0ZShkYXkgPSBsdWJyaWRhdGU6OndkYXkoCiAgICBsdWJyaWRhdGU6OnltZChlcF9iZWlnX2RhdCksCiAgICBsYWJlbCA9IFRSVUUsCiAgICBhYmJyID0gVFJVRQogICkpICU+JQogIGdncGxvdChhZXMoeCA9IGVwX2JlaWdfZGF0LAogICAgICAgICAgICAgeSA9IG4sCiAgICAgICAgICAgICBjb2xvciA9IGRheSkpICsKICBnZW9tX3BvaW50KCkgKwogIGxhYnMoCiAgICB0aXRsZSA9ICJNYW5pcHVsYXRpb25zIHBlciBkYXkgb2YgdGhlIHdlZWsiLAogICAgeSA9ICJNYW5pcHVsYXRpb25zIG4iLAogICAgeCA9ICJEYXRlIiwKICAgIGNvbG9yID0gIkRheSBvZiB0aGUgd2VlayIKICApICsKICAjIHNjYWxlX3lfbG9nMTAoKSArIAogIHNjYWxlX2ZpbGxfdmlyaWRpc19iKCkgKyAKICBmYWNldF9ncmlkKG1hbmlwdWxhdGlvbl90eXBlIH4gLiApICsgCiAgdGhlbWUobGVnZW5kLnBvc2l0aW9uID0gInRvcCIpICsKICB0aGVtZShzdHJpcC50ZXh0LnkgPSBlbGVtZW50X3RleHQoc2l6ZSA9IDgpKQpgYGAKCmBgYHtyfQpnZ3NhdmUoaGVyZSgiRmlnczIwMTlfMjAyMSIsICJmaWc0LnRpZiIpLCB3aWR0aCA9IDgsIGhlaWdodCA9IDYsIGRldmljZT0ndGlmZicsIGRwaT0zMDApCmBgYAo=