# PARTE 3: Interfaces de Conexión

# Importar paquetes y librerías

library(foreign)
library(haven)
library(tidyverse)
## ── Attaching core tidyverse packages ──────────────────────── tidyverse 2.0.0 ──
## ✔ dplyr     1.1.4     ✔ readr     2.1.5
## ✔ forcats   1.0.0     ✔ stringr   1.5.1
## ✔ ggplot2   3.5.1     ✔ tibble    3.2.1
## ✔ lubridate 1.9.4     ✔ tidyr     1.3.1
## ✔ purrr     1.0.4     
## ── Conflicts ────────────────────────────────────────── tidyverse_conflicts() ──
## ✖ dplyr::filter() masks stats::filter()
## ✖ dplyr::lag()    masks stats::lag()
## ℹ Use the conflicted package (<http://conflicted.r-lib.org/>) to force all conflicts to become errors
library(dplyr)

# Abrir base de datos y asignar a un data frame con el nombre de cohousing

cohousing <- read_sav("C:\\Users\\luich\\OneDrive\\Documentos\\Conexión de interfaces\\Cohousing.sav")
#Se requiere ingresar la dirección del archivo para su uso
#Usar "file.choose()" para encontrarlo en documentos

# Estructura y clase del df

str(cohousing)
## tibble [220 × 43] (S3: tbl_df/tbl/data.frame)
##  $ filtro1         : chr [1:220] "SI" "SI" "SI" "SI" ...
##   ..- attr(*, "format.spss")= chr "A2"
##   ..- attr(*, "display_width")= int 2
##  $ filtro2         : chr [1:220] "SI" "SI" "SI" "SI" ...
##   ..- attr(*, "format.spss")= chr "A2"
##   ..- attr(*, "display_width")= int 2
##  $ filtro3         : chr [1:220] "SI" "SI" "SI" "SI" ...
##   ..- attr(*, "format.spss")= chr "A2"
##   ..- attr(*, "display_width")= int 2
##  $ genero          : chr [1:220] "Femenino" "Femenino" "Masculino" "Masculino" ...
##   ..- attr(*, "format.spss")= chr "A9"
##   ..- attr(*, "display_width")= int 9
##  $ edad            : num [1:220] 31 32 36 30 25 27 25 35 27 28 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ cdresidencia    : chr [1:220] "CDMX" "Otro" "CDMX" "MTY" ...
##   ..- attr(*, "format.spss")= chr "A4"
##   ..- attr(*, "display_width")= int 4
##  $ tienestc        : chr [1:220] "SI" "SI" "SI" "SI" ...
##   ..- attr(*, "format.spss")= chr "A2"
##   ..- attr(*, "display_width")= int 2
##  $ conocesbchain   : chr [1:220] "SI" "NO" "NO" "SI" ...
##   ..- attr(*, "format.spss")= chr "A2"
##   ..- attr(*, "display_width")= int 2
##  $ conocescriptom  : chr [1:220] "SI" "NO" "SI" "SI" ...
##   ..- attr(*, "format.spss")= chr "A2"
##   ..- attr(*, "display_width")= int 2
##  $ conocesmonedadig: chr [1:220] "NO" "NO" "NO" "SI" ...
##   ..- attr(*, "format.spss")= chr "A2"
##   ..- attr(*, "display_width")= int 2
##  $ dispmonedadig   : chr [1:220] "SI" "SI" "NO" "SI" ...
##   ..- attr(*, "format.spss")= chr "A2"
##   ..- attr(*, "display_width")= int 2
##  $ salariomensual  : chr [1:220] "$11,000 - $17,000" "$5,000- $10,000" "$11,000 - $17,000" "$5,000- $10,000" ...
##   ..- attr(*, "format.spss")= chr "A17"
##   ..- attr(*, "display_width")= int 17
##  $ CFV1            : num [1:220] 5 3 6 7 4 7 5 7 4 7 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ CFV2            : num [1:220] 6 6 6 5 7 6 5 7 6 4 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ CFV3            : num [1:220] 6 7 7 6 7 6 5 7 6 6 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ CFV4            : num [1:220] 6 7 6 4 7 6 4 7 6 6 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ CFV5            : num [1:220] 6 7 6 4 7 7 6 7 7 4 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ OFERSERV1       : num [1:220] 5 4 6 5 4 6 7 6 6 6 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ OFERSERV2       : num [1:220] 4 4 7 5 4 6 7 7 6 4 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ OFERSERV3       : num [1:220] 5 4 7 5 4 6 6 7 6 4 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ OFERSERV4       : num [1:220] 6 4 6 5 3 6 6 4 6 6 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ DISPVC1         : num [1:220] 4 1 5 6 1 5 6 2 1 5 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ DISPVC2         : num [1:220] 5 4 4 6 1 6 7 5 1 5 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ DISPVC3         : num [1:220] 5 1 4 6 1 4 7 5 1 4 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ VARFIN1         : num [1:220] 5 4 7 6 6 7 7 6 7 4 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ VARFIN2         : num [1:220] 6 7 7 5 6 6 7 7 6 5 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ VARFIN3         : num [1:220] 7 7 6 5 6 6 7 7 6 6 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ VARFIN4         : num [1:220] 6 7 6 6 6 6 7 7 6 6 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ VARFIN5         : num [1:220] 5 7 7 5 6 7 7 7 5 7 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ OPPAGO1         : num [1:220] 6 4 5 4 6 6 5 7 5 7 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ OPPAGO2         : num [1:220] 7 4 5 5 6 6 6 7 5 7 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ OPPAGO3         : num [1:220] 4 4 5 4 6 6 5 6 5 7 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ DISCRIP1        : num [1:220] 5 4 2 4 6 5 4 1 5 5 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ DISCRIP2        : num [1:220] 4 4 2 3 6 6 5 1 5 5 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ DISCRIP3        : num [1:220] 5 4 2 3 6 5 5 1 5 5 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ DISCRIP4        : num [1:220] 3 4 2 2 6 6 5 1 6 5 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ CONCRIP1        : num [1:220] 4 4 1 6 6 4 3 5 6 1 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ CONCRIP2        : num [1:220] 5 4 1 5 6 7 3 4 6 1 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ CONCRIP3        : num [1:220] 2 1 1 4 6 4 2 1 6 1 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ INTCOMP1        : num [1:220] 3 7 4 2 4 6 4 1 6 5 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ INTCOMP2        : num [1:220] 5 5 4 4 4 5 5 3 5 4 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ INTCOMP3        : num [1:220] 4 5 4 7 4 6 5 3 6 4 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
##  $ INTCOMP4        : num [1:220] 5 5 4 7 4 6 5 3 5 4 ...
##   ..- attr(*, "format.spss")= chr "F8.2"
head(cohousing, 5)
## # A tibble: 5 × 43
##   filtro1 filtro2 filtro3 genero     edad cdresidencia tienestc conocesbchain
##   <chr>   <chr>   <chr>   <chr>     <dbl> <chr>        <chr>    <chr>        
## 1 SI      SI      SI      Femenino     31 CDMX         SI       SI           
## 2 SI      SI      SI      Femenino     32 Otro         SI       NO           
## 3 SI      SI      SI      Masculino    36 CDMX         SI       NO           
## 4 SI      SI      SI      Masculino    30 MTY          SI       SI           
## 5 SI      SI      SI      Masculino    25 CDMX         SI       NO           
## # ℹ 35 more variables: conocescriptom <chr>, conocesmonedadig <chr>,
## #   dispmonedadig <chr>, salariomensual <chr>, CFV1 <dbl>, CFV2 <dbl>,
## #   CFV3 <dbl>, CFV4 <dbl>, CFV5 <dbl>, OFERSERV1 <dbl>, OFERSERV2 <dbl>,
## #   OFERSERV3 <dbl>, OFERSERV4 <dbl>, DISPVC1 <dbl>, DISPVC2 <dbl>,
## #   DISPVC3 <dbl>, VARFIN1 <dbl>, VARFIN2 <dbl>, VARFIN3 <dbl>, VARFIN4 <dbl>,
## #   VARFIN5 <dbl>, OPPAGO1 <dbl>, OPPAGO2 <dbl>, OPPAGO3 <dbl>, DISCRIP1 <dbl>,
## #   DISCRIP2 <dbl>, DISCRIP3 <dbl>, DISCRIP4 <dbl>, CONCRIP1 <dbl>, …
class(cohousing)
## [1] "tbl_df"     "tbl"        "data.frame"
nrow(cohousing)
## [1] 220
view(cohousing)

# Renombrar salariomensual por valor_hipoteca

cohousing <-cohousing %>%
  rename(valor_hipoteca = salariomensual)

# Referencias de las características típicas de la vivienda

CFV1 - Prefiero una vivienda que sea adaptable a mis necesidades.

CFV2 - Me importa que mi vivienda sea amplia.

CFV3 - Prefiero viviendas con espacios abiertos.

CFV4 - Prefiero viviendas con espacios abiertos como terraza o roof garden.

CFV5 - Si pudiera, elegiría una vivienda espaciosa.

(La calificación mayor es 7, siendo “Totalmente de acuerdo” y la menor es 1, siendo “Totalmente en desacuerdo”)

# Análisis de respuestas

Obtener el promedio de las 5 preguntas que miden las características de la vivienda por género, para saber quienes son más positivos, los hombres o las mujeres y también para identificar cuál de las 5 características les resulta más importante.

df_vivienda <- cohousing %>%
  select (CFV1,CFV2, CFV3, CFV4, CFV5, genero) %>%
  group_by(genero) %>%
  summarise (promedio_CFV1 = mean(CFV1, na.rm = TRUE),
    promedio_CFV2 = mean(CFV2, na.rm = TRUE),
    promedio_CFV3 = mean(CFV3, na.rm = TRUE),
    promedio_CFV4 = mean(CFV4, na.rm = TRUE),
    promedio_CFV5 = mean(CFV5, na.rm = TRUE))
df_vivienda
## # A tibble: 2 × 6
##   genero   promedio_CFV1 promedio_CFV2 promedio_CFV3 promedio_CFV4 promedio_CFV5
##   <chr>            <dbl>         <dbl>         <dbl>         <dbl>         <dbl>
## 1 Femenino          6.03          5.58          5.96          5.90          6.23
## 2 Masculi…          6.02          5.44          5.78          5.69          5.78

Se puede ver que para las mujeres es más importante tener una vivienda más espaciosa. Por el lado de los hombres es más importante el tener una vivienda adaptable a sus necesidades. Además, el resultado nos muestra que las mujeres son más positivas ;)

# Obtener el promedio de edad de ambos géneros para identificar los clientes potenciales

#Muestra los dos géneros y su promedio de edad correspondiente
clientes_potenciales <- cohousing %>%
  select (genero, edad) %>%
  group_by(genero) %>%
  summarize (mean(edad))

clientes_potenciales
## # A tibble: 2 × 2
##   genero    `mean(edad)`
##   <chr>            <dbl>
## 1 Femenino          30.0
## 2 Masculino         31.5

El promedio de edad de las mujeres es de 29.97 y el de los hombres de 31.46.

# Análisis de clientes potenciales por ciudad

Se desea conocer, el género, edad, si tiene tarjeta de crédito, si conoce el block chain, si conoce la cripto moneda, el valor de la hipoteca y ciudad de residencia.

# Visualización de las columnas
colnames(cohousing)
##  [1] "filtro1"          "filtro2"          "filtro3"          "genero"          
##  [5] "edad"             "cdresidencia"     "tienestc"         "conocesbchain"   
##  [9] "conocescriptom"   "conocesmonedadig" "dispmonedadig"    "valor_hipoteca"  
## [13] "CFV1"             "CFV2"             "CFV3"             "CFV4"            
## [17] "CFV5"             "OFERSERV1"        "OFERSERV2"        "OFERSERV3"       
## [21] "OFERSERV4"        "DISPVC1"          "DISPVC2"          "DISPVC3"         
## [25] "VARFIN1"          "VARFIN2"          "VARFIN3"          "VARFIN4"         
## [29] "VARFIN5"          "OPPAGO1"          "OPPAGO2"          "OPPAGO3"         
## [33] "DISCRIP1"         "DISCRIP2"         "DISCRIP3"         "DISCRIP4"        
## [37] "CONCRIP1"         "CONCRIP2"         "CONCRIP3"         "INTCOMP1"        
## [41] "INTCOMP2"         "INTCOMP3"         "INTCOMP4"
#Seleccionar variables indicadas previamente
analisis_variables <- cohousing %>%
  select (genero, edad, tienestc, conocesbchain, conocescriptom, valor_hipoteca, cdresidencia)

# Análisis de clientes - Cd. de México

cohousing_cd_mexico <- analisis_variables %>%
  filter( cdresidencia == "CDMX")

#Visualizar el df
head(cohousing_cd_mexico, 10)
## # A tibble: 10 × 7
##    genero     edad tienestc conocesbchain conocescriptom valor_hipoteca   
##    <chr>     <dbl> <chr>    <chr>         <chr>          <chr>            
##  1 Femenino     31 SI       SI            SI             $11,000 - $17,000
##  2 Masculino    36 SI       NO            SI             $11,000 - $17,000
##  3 Masculino    25 SI       NO            SI             $5,000- $10,000  
##  4 Femenino     27 NO       NO            SI             $5,000- $10,000  
##  5 Masculino    25 NO       NO            SI             $5,000- $10,000  
##  6 Femenino     35 SI       SI            SI             $11,000 - $17,000
##  7 Femenino     27 SI       NO            SI             $11,000 - $17,000
##  8 Masculino    28 SI       SI            SI             $5,000- $10,000  
##  9 Femenino     27 SI       NO            SI             $5,000- $10,000  
## 10 Masculino    36 SI       SI            SI             Más de $25,000   
## # ℹ 1 more variable: cdresidencia <chr>

# Análisis de clientes - Guadalajara

cohousing_gdl <- analisis_variables %>%
  filter( cdresidencia == "GDL")

#Visualizar el df
head(cohousing_gdl, 10)
## # A tibble: 1 × 7
##   genero  edad tienestc conocesbchain conocescriptom valor_hipoteca cdresidencia
##   <chr>  <dbl> <chr>    <chr>         <chr>          <chr>          <chr>       
## 1 Femen…    32 SI       NO            NO             $11,000 - $17… GDL

# Análisis de clientes - Puebla

cohousing_puebla <- analisis_variables %>%
  filter( cdresidencia == "PUE")

#Visualizar el df
head(cohousing_puebla, 10)
## # A tibble: 10 × 7
##    genero     edad tienestc conocesbchain conocescriptom valor_hipoteca   
##    <chr>     <dbl> <chr>    <chr>         <chr>          <chr>            
##  1 Masculino    35 SI       NO            SI             $5,000- $10,000  
##  2 Femenino     30 SI       NO            NO             $5,000- $10,000  
##  3 Femenino     37 SI       NO            NO             $5,000- $10,000  
##  4 Femenino     36 SI       NO            NO             $5,000- $10,000  
##  5 Femenino     30 SI       NO            SI             $5,000- $10,000  
##  6 Femenino     35 NO       NO            SI             $5,000- $10,000  
##  7 Masculino    25 SI       NO            NO             $5,000- $10,000  
##  8 Femenino     30 SI       NO            SI             $5,000- $10,000  
##  9 Femenino     31 SI       NO            NO             $5,000- $10,000  
## 10 Femenino     30 SI       NO            SI             $18,000 - $24,000
## # ℹ 1 more variable: cdresidencia <chr>

El estudio se enfocará en la Cd. de México ya que los resultados anteriores nos indican que hay más encuestados que viven en la Cd. de México que pueden ser clientes potenciales.

Se necesita conocer a los encuestados que viven en la Cd. de México que tienen tarjeta de crédito y conocen Blockchain.

# Clientes potenciales CDMX por TDC y BC

#cd_mexico_tcybc debe contener las variables genero, edad, valor hipoteca, si tiene tarjeta de crédito y si conoce block chain
cd_mexico_tcybc <- cohousing_cd_mexico %>%
  select(-conocescriptom)%>% #Eliminar columna no requerida
  filter(tienestc == "SI" & conocesbchain == "SI")#Filtrar a los que si tienen tdc y conocen bchain
  
#Visualizar el df
head(cd_mexico_tcybc, 10)
## # A tibble: 10 × 6
##    genero     edad tienestc conocesbchain valor_hipoteca    cdresidencia
##    <chr>     <dbl> <chr>    <chr>         <chr>             <chr>       
##  1 Femenino     31 SI       SI            $11,000 - $17,000 CDMX        
##  2 Femenino     35 SI       SI            $11,000 - $17,000 CDMX        
##  3 Masculino    28 SI       SI            $5,000- $10,000   CDMX        
##  4 Masculino    36 SI       SI            Más de $25,000    CDMX        
##  5 Masculino    29 SI       SI            $11,000 - $17,000 CDMX        
##  6 Masculino    28 SI       SI            $18,000 - $24,000 CDMX        
##  7 Femenino     34 SI       SI            $11,000 - $17,000 CDMX        
##  8 Masculino    26 SI       SI            $11,000 - $17,000 CDMX        
##  9 Femenino     25 SI       SI            $5,000- $10,000   CDMX        
## 10 Masculino    25 SI       SI            $11,000 - $17,000 CDMX

# Guardar dataframe final - CDMX

# Guardar en CSV
write.csv(cd_mexico_tcybc, "cd_mexico_tcybc.csv", row.names = FALSE)

#Llamar librería para guardar en Excel
library(openxlsx)
## Warning: package 'openxlsx' was built under R version 4.4.3
# Guardar en Excel
write.xlsx(cd_mexico_tcybc, "cd_mexico_tcybc.xlsx")
LS0tDQp0aXRsZTogIkNvbmV4acOzbiBkZSBpbnRlcmZhY2VzIg0KYXV0aG9yOiAiTHVpcyBNZW5kb3phIFZpbGxhc2XDsW9yIEEwMDgzODUyNCINCmRhdGU6ICIyMDI1LTAzLTA0Ig0Kb3V0cHV0OiANCiAgaHRtbF9kb2N1bWVudDoNCiAgICB0b2M6IFRSVUUNCiAgICB0b2NfZmxvYXQ6IFRSVUUNCiAgICBjb2RlX2Rvd25sb2FkOiBUUlVFDQogICAgdGhlbWU6IGNlcnVsZWFuDQogIA0KLS0tDQoNCiM8c3BhbiBzdHlsZSA9ICJjb2xvcjogYmx1ZTsiPiBQQVJURSAzOiBJbnRlcmZhY2VzIGRlIENvbmV4acOzbiA8L3NwYW4+DQoNCg0KIzxzcGFuIHN0eWxlID0gImNvbG9yOiBibHVlOyI+IEltcG9ydGFyIHBhcXVldGVzIHkgbGlicmVyw61hcyA8L3NwYW4+DQpgYGB7cn0NCmxpYnJhcnkoZm9yZWlnbikNCmxpYnJhcnkoaGF2ZW4pDQpsaWJyYXJ5KHRpZHl2ZXJzZSkNCmxpYnJhcnkoZHBseXIpDQpgYGANCg0KIzxzcGFuIHN0eWxlID0gImNvbG9yOiBibHVlOyI+IEFicmlyIGJhc2UgZGUgZGF0b3MgeSBhc2lnbmFyIGEgdW4gZGF0YSBmcmFtZSBjb24gZWwgbm9tYnJlIGRlIGNvaG91c2luZyA8L3NwYW4+DQpgYGB7cn0NCmNvaG91c2luZyA8LSByZWFkX3NhdigiQzpcXFVzZXJzXFxsdWljaFxcT25lRHJpdmVcXERvY3VtZW50b3NcXENvbmV4acOzbiBkZSBpbnRlcmZhY2VzXFxDb2hvdXNpbmcuc2F2IikNCiNTZSByZXF1aWVyZSBpbmdyZXNhciBsYSBkaXJlY2Npw7NuIGRlbCBhcmNoaXZvIHBhcmEgc3UgdXNvDQojVXNhciAiZmlsZS5jaG9vc2UoKSIgcGFyYSBlbmNvbnRyYXJsbyBlbiBkb2N1bWVudG9zDQpgYGANCg0KIzxzcGFuIHN0eWxlID0gImNvbG9yOiBibHVlOyI+IEVzdHJ1Y3R1cmEgeSBjbGFzZSBkZWwgZGYgPC9zcGFuPg0KYGBge3J9DQpzdHIoY29ob3VzaW5nKQ0KaGVhZChjb2hvdXNpbmcsIDUpDQpjbGFzcyhjb2hvdXNpbmcpDQpucm93KGNvaG91c2luZykNCnZpZXcoY29ob3VzaW5nKQ0KYGBgDQoNCiM8c3BhbiBzdHlsZSA9ICJjb2xvcjogYmx1ZTsiPiBSZW5vbWJyYXIgc2FsYXJpb21lbnN1YWwgcG9yIHZhbG9yX2hpcG90ZWNhIDwvc3Bhbj4NCmBgYHtyfQ0KY29ob3VzaW5nIDwtY29ob3VzaW5nICU+JQ0KICByZW5hbWUodmFsb3JfaGlwb3RlY2EgPSBzYWxhcmlvbWVuc3VhbCkNCmBgYA0KDQojPHNwYW4gc3R5bGUgPSAiY29sb3I6IGJsdWU7Ij4gUmVmZXJlbmNpYXMgZGUgbGFzIGNhcmFjdGVyw61zdGljYXMgdMOtcGljYXMgZGUgbGEgdml2aWVuZGEgPC9zcGFuPg0KDQpDRlYxIC0gUHJlZmllcm8gdW5hIHZpdmllbmRhIHF1ZSBzZWEgYWRhcHRhYmxlIGEgbWlzIG5lY2VzaWRhZGVzLg0KDQpDRlYyIC0gTWUgaW1wb3J0YSBxdWUgbWkgdml2aWVuZGEgc2VhIGFtcGxpYS4NCg0KQ0ZWMyAtIFByZWZpZXJvIHZpdmllbmRhcyBjb24gZXNwYWNpb3MgYWJpZXJ0b3MuDQoNCkNGVjQgLSBQcmVmaWVybyB2aXZpZW5kYXMgY29uIGVzcGFjaW9zIGFiaWVydG9zIGNvbW8gdGVycmF6YSBvIHJvb2YgZ2FyZGVuLg0KDQpDRlY1IC0gU2kgcHVkaWVyYSwgZWxlZ2lyacyBYSB1bmEgdml2aWVuZGEgZXNwYWNpb3NhLg0KDQooTGEgY2FsaWZpY2FjacOzbiBtYXlvciBlcyA3LCBzaWVuZG8gIlRvdGFsbWVudGUgZGUgYWN1ZXJkbyIgeSBsYSBtZW5vciBlcyAxLCBzaWVuZG8gIlRvdGFsbWVudGUgZW4gZGVzYWN1ZXJkbyIpDQoNCg0KIzxzcGFuIHN0eWxlID0gImNvbG9yOiBibHVlOyI+IEFuw6FsaXNpcyBkZSByZXNwdWVzdGFzIDwvc3Bhbj4NCg0KT2J0ZW5lciBlbCBwcm9tZWRpbyBkZSBsYXMgNSBwcmVndW50YXMgcXVlIG1pZGVuIGxhcyBjYXJhY3RlcsOtc3RpY2FzIGRlIGxhIHZpdmllbmRhIHBvciBnw6luZXJvLCBwYXJhIHNhYmVyIHF1aWVuZXMgc29uIG3DoXMgcG9zaXRpdm9zLCBsb3MgaG9tYnJlcyBvIGxhcyBtdWplcmVzIHkgdGFtYmnDqW4gcGFyYSBpZGVudGlmaWNhciBjdcOhbCBkZSBsYXMgNSBjYXJhY3RlcsOtc3RpY2FzIGxlcyByZXN1bHRhIG3DoXMgaW1wb3J0YW50ZS4NCg0KYGBge3J9DQpkZl92aXZpZW5kYSA8LSBjb2hvdXNpbmcgJT4lDQogIHNlbGVjdCAoQ0ZWMSxDRlYyLCBDRlYzLCBDRlY0LCBDRlY1LCBnZW5lcm8pICU+JQ0KICBncm91cF9ieShnZW5lcm8pICU+JQ0KICBzdW1tYXJpc2UgKHByb21lZGlvX0NGVjEgPSBtZWFuKENGVjEsIG5hLnJtID0gVFJVRSksDQogICAgcHJvbWVkaW9fQ0ZWMiA9IG1lYW4oQ0ZWMiwgbmEucm0gPSBUUlVFKSwNCiAgICBwcm9tZWRpb19DRlYzID0gbWVhbihDRlYzLCBuYS5ybSA9IFRSVUUpLA0KICAgIHByb21lZGlvX0NGVjQgPSBtZWFuKENGVjQsIG5hLnJtID0gVFJVRSksDQogICAgcHJvbWVkaW9fQ0ZWNSA9IG1lYW4oQ0ZWNSwgbmEucm0gPSBUUlVFKSkNCmRmX3ZpdmllbmRhDQoNCmBgYA0KU2UgcHVlZGUgdmVyIHF1ZSBwYXJhIGxhcyBtdWplcmVzIGVzIG3DoXMgaW1wb3J0YW50ZSB0ZW5lciB1bmEgdml2aWVuZGEgbcOhcyBlc3BhY2lvc2EuIFBvciBlbCBsYWRvIGRlIGxvcyBob21icmVzIGVzIG3DoXMgaW1wb3J0YW50ZSBlbCB0ZW5lciB1bmEgdml2aWVuZGEgYWRhcHRhYmxlIGEgc3VzIG5lY2VzaWRhZGVzLiBBZGVtw6FzLCBlbCByZXN1bHRhZG8gbm9zIG11ZXN0cmEgcXVlIGxhcyBtdWplcmVzIHNvbiBtw6FzIHBvc2l0aXZhcyA7KQ0KDQoNCg0KIzxzcGFuIHN0eWxlID0gImNvbG9yOiBibHVlOyI+IE9idGVuZXIgZWwgcHJvbWVkaW8gZGUgZWRhZCBkZSBhbWJvcyBnw6luZXJvcyBwYXJhIGlkZW50aWZpY2FyIGxvcyBjbGllbnRlcyBwb3RlbmNpYWxlcyA8L3NwYW4+DQpgYGB7cn0NCiNNdWVzdHJhIGxvcyBkb3MgZ8OpbmVyb3MgeSBzdSBwcm9tZWRpbyBkZSBlZGFkIGNvcnJlc3BvbmRpZW50ZQ0KY2xpZW50ZXNfcG90ZW5jaWFsZXMgPC0gY29ob3VzaW5nICU+JQ0KICBzZWxlY3QgKGdlbmVybywgZWRhZCkgJT4lDQogIGdyb3VwX2J5KGdlbmVybykgJT4lDQogIHN1bW1hcml6ZSAobWVhbihlZGFkKSkNCg0KY2xpZW50ZXNfcG90ZW5jaWFsZXMNCg0KYGBgDQoNCkVsIHByb21lZGlvIGRlIGVkYWQgZGUgbGFzIG11amVyZXMgZXMgZGUgMjkuOTcgeSBlbCBkZSBsb3MgaG9tYnJlcyBkZSAzMS40Ni4NCg0KIzxzcGFuIHN0eWxlID0gImNvbG9yOiBibHVlOyI+IEFuw6FsaXNpcyBkZSBjbGllbnRlcyBwb3RlbmNpYWxlcyBwb3IgY2l1ZGFkIDwvc3Bhbj4NCg0KU2UgZGVzZWEgY29ub2NlciwgZWwgZ8OpbmVybywgZWRhZCwgc2kgdGllbmUgdGFyamV0YSBkZSBjcsOpZGl0bywgc2kgY29ub2NlIGVsIGJsb2NrIGNoYWluLCBzaSBjb25vY2UgbGEgY3JpcHRvIG1vbmVkYSwgZWwgdmFsb3IgZGUgbGEgaGlwb3RlY2EgeSBjaXVkYWQgZGUgcmVzaWRlbmNpYS4NCg0KYGBge3J9DQojIFZpc3VhbGl6YWNpw7NuIGRlIGxhcyBjb2x1bW5hcw0KY29sbmFtZXMoY29ob3VzaW5nKQ0KI1NlbGVjY2lvbmFyIHZhcmlhYmxlcyBpbmRpY2FkYXMgcHJldmlhbWVudGUNCmFuYWxpc2lzX3ZhcmlhYmxlcyA8LSBjb2hvdXNpbmcgJT4lDQogIHNlbGVjdCAoZ2VuZXJvLCBlZGFkLCB0aWVuZXN0YywgY29ub2Nlc2JjaGFpbiwgY29ub2Nlc2NyaXB0b20sIHZhbG9yX2hpcG90ZWNhLCBjZHJlc2lkZW5jaWEpDQpgYGANCg0KIzxzcGFuIHN0eWxlID0gImNvbG9yOiBibHVlOyI+IEFuw6FsaXNpcyBkZSBjbGllbnRlcyAtIENkLiBkZSBNw6l4aWNvIDwvc3Bhbj4NCmBgYHtyfQ0KY29ob3VzaW5nX2NkX21leGljbyA8LSBhbmFsaXNpc192YXJpYWJsZXMgJT4lDQogIGZpbHRlciggY2RyZXNpZGVuY2lhID09ICJDRE1YIikNCg0KI1Zpc3VhbGl6YXIgZWwgZGYNCmhlYWQoY29ob3VzaW5nX2NkX21leGljbywgMTApDQpgYGANCg0KDQojPHNwYW4gc3R5bGUgPSAiY29sb3I6IGJsdWU7Ij4gQW7DoWxpc2lzIGRlIGNsaWVudGVzIC0gR3VhZGFsYWphcmEgPC9zcGFuPg0KYGBge3J9DQpjb2hvdXNpbmdfZ2RsIDwtIGFuYWxpc2lzX3ZhcmlhYmxlcyAlPiUNCiAgZmlsdGVyKCBjZHJlc2lkZW5jaWEgPT0gIkdETCIpDQoNCiNWaXN1YWxpemFyIGVsIGRmDQpoZWFkKGNvaG91c2luZ19nZGwsIDEwKQ0KYGBgDQoNCg0KIzxzcGFuIHN0eWxlID0gImNvbG9yOiBibHVlOyI+IEFuw6FsaXNpcyBkZSBjbGllbnRlcyAtIFB1ZWJsYSA8L3NwYW4+DQpgYGB7cn0NCmNvaG91c2luZ19wdWVibGEgPC0gYW5hbGlzaXNfdmFyaWFibGVzICU+JQ0KICBmaWx0ZXIoIGNkcmVzaWRlbmNpYSA9PSAiUFVFIikNCg0KI1Zpc3VhbGl6YXIgZWwgZGYNCmhlYWQoY29ob3VzaW5nX3B1ZWJsYSwgMTApDQpgYGANCg0KRWwgZXN0dWRpbyBzZSBlbmZvY2Fyw6EgZW4gbGEgQ2QuIGRlIE3DqXhpY28geWEgcXVlIGxvcyByZXN1bHRhZG9zIGFudGVyaW9yZXMgbm9zIGluZGljYW4gcXVlIGhheSBtw6FzIGVuY3Vlc3RhZG9zIHF1ZSB2aXZlbiBlbiBsYSBDZC4gZGUgTcOpeGljbyBxdWUgcHVlZGVuIHNlciBjbGllbnRlcyBwb3RlbmNpYWxlcy4NCg0KU2UgbmVjZXNpdGEgY29ub2NlciBhIGxvcyBlbmN1ZXN0YWRvcyBxdWUgdml2ZW4gZW4gbGEgQ2QuIGRlIE3DqXhpY28gcXVlIHRpZW5lbiB0YXJqZXRhIGRlIGNyw6lkaXRvIHkgY29ub2NlbiBCbG9ja2NoYWluLg0KDQojPHNwYW4gc3R5bGUgPSAiY29sb3I6IGJsdWU7Ij4gQ2xpZW50ZXMgcG90ZW5jaWFsZXMgQ0RNWCBwb3IgVERDIHkgQkMgPC9zcGFuPg0KYGBge3J9DQojY2RfbWV4aWNvX3RjeWJjIGRlYmUgY29udGVuZXIgbGFzIHZhcmlhYmxlcyBnZW5lcm8sIGVkYWQsIHZhbG9yIGhpcG90ZWNhLCBzaSB0aWVuZSB0YXJqZXRhIGRlIGNyw6lkaXRvIHkgc2kgY29ub2NlIGJsb2NrIGNoYWluDQpjZF9tZXhpY29fdGN5YmMgPC0gY29ob3VzaW5nX2NkX21leGljbyAlPiUNCiAgc2VsZWN0KC1jb25vY2VzY3JpcHRvbSklPiUgI0VsaW1pbmFyIGNvbHVtbmEgbm8gcmVxdWVyaWRhDQogIGZpbHRlcih0aWVuZXN0YyA9PSAiU0kiICYgY29ub2Nlc2JjaGFpbiA9PSAiU0kiKSNGaWx0cmFyIGEgbG9zIHF1ZSBzaSB0aWVuZW4gdGRjIHkgY29ub2NlbiBiY2hhaW4NCiAgDQojVmlzdWFsaXphciBlbCBkZg0KaGVhZChjZF9tZXhpY29fdGN5YmMsIDEwKQ0KDQpgYGANCg0KDQojPHNwYW4gc3R5bGUgPSAiY29sb3I6IGJsdWU7Ij4gR3VhcmRhciBkYXRhZnJhbWUgZmluYWwgLSBDRE1YIDwvc3Bhbj4NCmBgYHtyfQ0KIyBHdWFyZGFyIGVuIENTVg0Kd3JpdGUuY3N2KGNkX21leGljb190Y3liYywgImNkX21leGljb190Y3liYy5jc3YiLCByb3cubmFtZXMgPSBGQUxTRSkNCg0KI0xsYW1hciBsaWJyZXLDrWEgcGFyYSBndWFyZGFyIGVuIEV4Y2VsDQpsaWJyYXJ5KG9wZW54bHN4KQ0KDQojIEd1YXJkYXIgZW4gRXhjZWwNCndyaXRlLnhsc3goY2RfbWV4aWNvX3RjeWJjLCAiY2RfbWV4aWNvX3RjeWJjLnhsc3giKQ0KYGBgDQoNCg0K