1. Introducción

El arte generativo es una forma contemporánea de creación artística, hace referencia al arte que en su totalidad o parcialmente ha sido creado con el uso de un sistema autónomo (Urgiles, 2019). Se encuentra presente en la música, el diseño y la pintura. En este reporte se genera una colección de 10 piezas de arte generativo creadas a través de algoritmos usando funciones trigonométricas hipérbolicas, distribuciones de probabilidad multivariadas y métodos de aprendizaje estadístico.

2. Piezas

Pieza 1 - Ying-Yang fragmentado

La siguiente pieza se crea inspirada en las figuras de voronoi, que consisten en construcciones geométricas que permiten realizar particiones del plano o del espacio. Los pasos a seguir en la construcción fueron:

    1. Generar un dos sets de números aleatorios (x,y), calcular las distancias entre los puntos y guardar estos datos en un dataframe. Una vista del dataframe generado es:
Tabla 1: Datos para gráficar
x y dist
324 193 109.6586
167 111 231.1060
129 485 251.9246
418 342 125.2517
471 85 274.7108
  1. Con el set de datos y apoyándose en las librerias ggplot2yggvoronoi, generamos un procedimiento adaptado con las funciones cosh y tanh para realizar el gráfico.

En el resultado obtenido se observa la figura de voronoi generada y con su particular forma de ying-yang. Se escoge la tonalidad azul por ser la favorita del autor.

Pieza 1: Ying-Yang fragmentado

Pieza 2 - simetría invertida

La siguiente pieza, se crea a partir de un círculo y con la función sinh se adiciona la perfecta simetría de la figura representada en las dos formas salientes del radio. Nuevamente se aprovecha ggplot2 y variando las constantes y valores de la función e llega a esta figura.

Pieza 2: simetría invertida

Pieza 3 - Distorsión Gaussiana

La pieza denominada Distorsión Gaussiana, se generó con apoyo de la función mvrnorm para poder así crear muestras a partir de la Distribución Normal Multivariada especificada. Luego, para crear la figura se empleó ggplot2. El resultado que se obtuvo fue el siguiente:

Pieza 3: Distorsión Gaussiana

Pieza 4 - La Normalidad de Bessel

Con apoyo de la función Bessel y rlnorm se diseñó esta pieza. Es decir, la figura tiene su base en una combinación entre las funciones de Bessel y la Distribución Lognormal Multivariada. A consecuencia de dicha unión se obtuvo la siguiente obra de arte:

Pieza 4: La Normalidad de Bessel

Pieza 5 - Rainbow.

La pieza denominada Rainbow, se generó con apoyo dedatos normales para poder así crear muestras a partir de registros los cuales son año, grupo y valores. Luego, para crear la figura se empleó ggplot. El resultado que se obtuvo fue el siguiente:

Pieza 5: Rainbow

Pieza 6 - Gamma Big Bang

La pieza denominada Gamma Big Bang, se generó con apoyo de la función rgamma para poder así crear muestras aleatorias a partir de la Distribución Gamma especificada. Luego, para crear la figura se empleó el devtoolsdjnavarro/jasmines. El resultado que se obtuvo fue el siguiente:

Pieza 6: Gamma Big Bang

Pieza 7 - Tornado

La siguiente pieza, se crea a partir del experimento tornado de StarCircle, creando un aspecto tridimensional, casi esférico (Kumar, 2020). El tornado presenta pequeñas modificaciones para estar más cerrado, aumentando su secuencia, cambiando la función (cos(y+x)+1.3*y) por (cos(y+x)+10*y) en el eje X y (sin(x+y)+2.3*x) por (sin(x+y)+0.1*x) en el eje Y. Nuevamente se hace usos de ggplot2 llegando a esta figura.

Pieza 7: Tornado

Pieza 8 - Casualidad

La siguiente pieza, se crea a partir de los datos X y Y de la pieza 3, Distorsión Gaussiana, realizando todas las combinaciones posibles entre los dos factores con la función expand.grid() y la función (cos(y+x)+1.3*y) en el eje X y (sin(x+y)+2.3*x) en el eje Y. Dando como resultado la siguiente figura.

Pieza 8: Casualidad

Pieza 9 - tree_1

Para el tree_1.png se muestra una grafica creada a partir de random forest generado con un gran dataset de sklearn, es interesante ver como con la gran cantidad de datos salen muchas ramas que pueden parecer una granja de hormigas o un enorme árbol genealógico o de evolución.

Pieza 9: tree_1

Pieza 10 - tree_2

Para el tree_2.png se muestra igualmente una grafica generada con random forest y el mismo dataset, es menos llamativo y al parecer menos complejo pero realmente puede variar más visualmente, las formas que muestra pueden parecerse a un cerebro, un elefante, un cráneo… depende la percepción de quein lo esté viendo y de como se alla generado la imagen aleatoriamente, todos los pequeños letreros o cuadros de la imagen son valores de las hojas del random forest, los valores del dataset son irrelevantes para lo que estamos haciendo, sólo pueden variar el color de cada uno de estos letreros naranjas.

Pieza 10: tree_2

3. Conclusiones

  • Las piezas artísticas creadas por medio de las técnicas afianzadas en el curso son una muestra de lo bello que es la Ciencia. Es decir, no solamente aplicar métodos matemáticos y estadísticos para solucionar problemas de la cotidianidad, sino ahora para hacer de ello algo más tangible, proyectado en una serie de imágenes, para que se pueda apreciar también por personas que no necesariamente están inmersas en este mundo las ciencias formales.

  • Fue un excelente reto hacer este proyecto, ya que ninguno estaba familiarizado con el concepto de “Arte Generativo”. Además, considerando que se está culminando el período académico sirvió de terapia antiestrés realizar cada figura.

  • Las piezas que se generaron para este trabajo van desde metodologías como “random forest”, hasta “funciones de Bessel”, lo cual implica que se proporcionó gran variedad de contenido y hace que implícitamente se note la seriedad y compromiso con el que se tomó el último trabajo para dicho curso.

4. Enlaces de interés

Usted puede revisar el código y los datos usados en este proyecto en nuestro repositorio en Github

5. Referencias

LS0tDQp0aXRsZTogIkFydGUgZ2VuZXJhdGl2byINCmF1dGhvcjogIkplc3VzIERhdmlkIFNhbnRvcyBNb250ZXMsIEtsZWlkZXIgU3RpdmVuIFbDoXNxdWV6IEfDs21leiwgRGFuaWVsIEFuZHLDqXMgVG9ybyBBZ3VpcnJlLCBKZWxzc2luIERvbm5vdmFuIFJvYmxlZG8gTWVuYSwgSnVhbiBFc3RlYmFuIENhcnZhamFsIE1vbGluYS4iDQpkYXRlOiAiMDgvMDIvMjAyMiINCm91dHB1dDogDQogIGh0bWxfZG9jdW1lbnQ6DQogICAgdGhlbWU6IHNwYWNlbGFiDQogICAgY29kZV9mb2xkaW5nOiBoaWRlDQogICAgY29kZV9kb3dubG9hZDogeWVzDQogICAgZGZfcHJpbnQ6IHBhZ2VkDQogICAgdG9jOiB0cnVlDQogICAgdG9jX2Zsb2F0OiANCiAgICAgIGNvbGFwc2U6IGZhbHNlDQotLS0NCg0KYGBge3Igc2V0dXAsIGluY2x1ZGU9RkFMU0V9DQprbml0cjo6b3B0c19jaHVuayRzZXQoZWNobyA9IFRSVUUpDQpgYGANCg0KDQojIyAxLiBJbnRyb2R1Y2Npw7NuDQoNCg0KRWwgYXJ0ZSBnZW5lcmF0aXZvIGVzIHVuYSBmb3JtYSBjb250ZW1wb3LDoW5lYSBkZSBjcmVhY2nDs24gYXJ0w61zdGljYSwgaGFjZSByZWZlcmVuY2lhIGFsIGFydGUgcXVlIGVuIHN1IHRvdGFsaWRhZCBvIHBhcmNpYWxtZW50ZSBoYSBzaWRvIGNyZWFkbyBjb24gZWwgdXNvIGRlIHVuIHNpc3RlbWEgYXV0w7Nub21vIChVcmdpbGVzLCAyMDE5KS4gU2UgZW5jdWVudHJhIHByZXNlbnRlIGVuIGxhIG3DunNpY2EsIGVsIGRpc2XDsW8geSBsYSBwaW50dXJhLiBFbiBlc3RlIHJlcG9ydGUgc2UgZ2VuZXJhIHVuYSBjb2xlY2Npw7NuIGRlIDEwIHBpZXphcyBkZSBhcnRlIGdlbmVyYXRpdm8gY3JlYWRhcyBhIHRyYXbDqXMgZGUgYWxnb3JpdG1vcyB1c2FuZG8gZnVuY2lvbmVzIHRyaWdvbm9tw6l0cmljYXMgaGlww6lyYm9saWNhcywgZGlzdHJpYnVjaW9uZXMgZGUgcHJvYmFiaWxpZGFkIG11bHRpdmFyaWFkYXMgeSBtw6l0b2RvcyBkZSBhcHJlbmRpemFqZSBlc3RhZMOtc3RpY28uDQoNCg0KDQoNCg0KIyMgMi4gUGllemFzDQoNCmBgYHtyIG1lc3NhZ2U9RkFMU0UsIHdhcm5pbmc9RkFMU0UsIHJlc3VsdHMgPSAnaGlkZScsIGVjaG89RiwgaW5jbHVkZT1GQUxTRSB9DQoNCiNjYXJnYXMgbGlicmVyw61hcyBuZWNlc2FyaWFzDQoNCiNpbnN0YWxsLnBhY2thZ2VzKCJnZ3Zvcm9ub2kiKQ0KDQpsaWJyYXJ5KGdncGxvdDIpDQpsaWJyYXJ5KGdndm9yb25vaSkNCmxpYnJhcnkoZHBseXIpDQpsaWJyYXJ5KGthYmxlRXh0cmEpDQoNCmBgYA0KDQoNCg0KIyMjIFBpZXphIDEgLSBZaW5nLVlhbmcgZnJhZ21lbnRhZG8NCg0KTGEgc2lndWllbnRlIHBpZXphIHNlIGNyZWEgaW5zcGlyYWRhIGVuIGxhcyBmaWd1cmFzIGRlIFt2b3Jvbm9pXShodHRwczovL3JlcG9zaXRvcmlvLnVuaWNhbi5lcy94bWx1aS9iaXRzdHJlYW0vaGFuZGxlLzEwOTAyLzE4ODg1L09ydGVnYURlbENhbXBvTHVjaWEucGRmP3NlcXVlbmNlPTEmaXNBbGxvd2VkPXkpLCBxdWUgY29uc2lzdGVuIGVuIGNvbnN0cnVjY2lvbmVzIGdlb23DqXRyaWNhcyBxdWUgcGVybWl0ZW4gcmVhbGl6YXIgcGFydGljaW9uZXMgZGVsIHBsYW5vIG8gZGVsIGVzcGFjaW8uIExvcyBwYXNvcyBhIHNlZ3VpciBlbiBsYSBjb25zdHJ1Y2Npw7NuIGZ1ZXJvbjoNCg0KKiAxLiBHZW5lcmFyIHVuIGRvcyBzZXRzIGRlIG7Dum1lcm9zIGFsZWF0b3Jpb3MgKHgseSksIGNhbGN1bGFyIGxhcyBkaXN0YW5jaWFzIGVudHJlIGxvcyBwdW50b3MgeSBndWFyZGFyIGVzdG9zIGRhdG9zIGVuIHVuIGRhdGFmcmFtZS4gVW5hIHZpc3RhIGRlbCBkYXRhZnJhbWUgZ2VuZXJhZG8gZXM6DQoNCmBgYHtyIG1lc3NhZ2U9RkFMU0UsIHdhcm5pbmc9RkFMU0UgLCBlY2hvPUYgfQ0KI2xpYnJhcnkoZ2dwbG90MikNCiNsaWJyYXJ5KGdndm9yb25vaSkNCg0KIyBHZW5lcmFuZG8gZGF0b3MgcGFyYSBncsOhZmljYXINCg0Kc2V0LnNlZWQoMSkNCnggPC0gc2FtcGxlKDE6NTAwLCBzaXplID0gNTAwKQ0KeSA8LSBzYW1wbGUoMTo1MDAsIHNpemUgPSA1MDApDQpkaXN0IDwtIHNxcnQoKHggLSAzMDApIF4gMiArICh5IC0gMzAwKSBeIDIpDQoNCmRmIDwtIGRhdGEuZnJhbWUoeCwgeSwgZGlzdCA9IGRpc3QpDQpkYXRvcyA8LSBoZWFkKGRmLCBuPTUpDQoNCmtibChkYXRvcyxjYXB0aW9uID0gIlRhYmxhIDE6IERhdG9zIHBhcmEgZ3LDoWZpY2FyIikgJT4lIGthYmxlX3N0eWxpbmcobGF0ZXhfb3B0aW9ucyA9IGMoInN0cmlwZWQiLCJjb25kZW5zZWQiLCJIT0xEX3Bvc2l0aW9uIiksIHBvc2l0aW9uID0gImNlbnRlciIsZnVsbF93aWR0aCA9IEZBTFNFKQ0KYGBgDQoyLiBDb24gZWwgc2V0IGRlIGRhdG9zIHkgYXBvecOhbmRvc2UgZW4gbGFzIGxpYnJlcmlhcyBgZ2dwbG90MmB5YGdndm9yb25vaWAsIGdlbmVyYW1vcyB1biBwcm9jZWRpbWllbnRvIGFkYXB0YWRvIGNvbiBsYXMgZnVuY2lvbmVzIGNvc2ggeSB0YW5oIHBhcmEgcmVhbGl6YXIgZWwgZ3LDoWZpY28uICANCg0KYGBge3IgbWVzc2FnZT1GQUxTRSwgd2FybmluZz1GQUxTRSAsIGVjaG89RiwgaW5jbHVkZT1GQUxTRSAgfQ0KIyBjb2xhDQpzIDwtIHNlcSgwLCAxICogcGksIGxlbmd0aC5vdXQgPSAzMDAwKQ0KY29sYSA8LSBkYXRhLmZyYW1lKHggPSAxMDAgKiAoMSArIGNvc2gocykpLA0KICAgICAgICAgICAgICAgICAgICAgIHkgPSAyMDAgKiAoMSArIHRhbmgocykpLA0KICAgICAgICAgICAgICAgICAgICAgIGdydXBvID0gcmVwKDEsIDMwMDApKQ0KDQpwbmcoImFydGUxLnBuZyIpDQoNCmdncGxvdChkZiwgYWVzKHgsIHksIGZpbGwgPSBkaXN0KSkgKw0KICBnZW9tX3Zvcm9ub2kob3V0bGluZSA9IGNvbGEsDQogICAgICAgICAgICAgICBjb2xvciA9IDEsIHNpemUgPSAwLjEpICsNCiAgc2NhbGVfZmlsbF9ncmFkaWVudChsb3cgPSAiI0I5RERGMSIsICAjIiNCOURERjEiDQogICAgICAgICAgICAgICAgICAgICAgaGlnaCA9ICIjMkE1NzgzIiwgICMyQTU3ODMNCiAgICAgICAgICAgICAgICAgICAgICBndWlkZSA9ICJub25lIikgKw0KICB0aGVtZV92b2lkKCkgKw0KICBjb29yZF9wb2xhcigpDQoNCmRldi5vZmYoKQ0KIA0KYGBgDQpFbiBlbCByZXN1bHRhZG8gb2J0ZW5pZG8gc2Ugb2JzZXJ2YSBsYSBmaWd1cmEgZGUgdm9yb25vaSBnZW5lcmFkYSB5IGNvbiBzdSBwYXJ0aWN1bGFyIGZvcm1hIGRlIHlpbmcteWFuZy4gU2UgZXNjb2dlIGxhIHRvbmFsaWRhZCBhenVsIHBvciBzZXIgbGEgZmF2b3JpdGEgZGVsIGF1dG9yLg0KDQohW1BpZXphIDE6IFlpbmctWWFuZyBmcmFnbWVudGFkb10oYXJ0ZTEucG5nKXt3aXRoZD04MCV9DQoNCiMjIyBQaWV6YSAyIC0gc2ltZXRyw61hIGludmVydGlkYQ0KDQpMYSBzaWd1aWVudGUgcGllemEsIHNlIGNyZWEgYSBwYXJ0aXIgZGUgdW4gY8OtcmN1bG8geSBjb24gbGEgZnVuY2nDs24gc2luaCBzZSBhZGljaW9uYSBsYSBwZXJmZWN0YSBzaW1ldHLDrWEgZGUgbGEgZmlndXJhIHJlcHJlc2VudGFkYSBlbiBsYXMgZG9zIGZvcm1hcyBzYWxpZW50ZXMgZGVsIHJhZGlvLiBOdWV2YW1lbnRlIHNlIGFwcm92ZWNoYSBgZ2dwbG90MmAgeSB2YXJpYW5kbyBsYXMgY29uc3RhbnRlcyB5IHZhbG9yZXMgZGUgbGEgZnVuY2nDs24gZSBsbGVnYSBhIGVzdGEgZmlndXJhLg0KDQpgYGB7ciBtZXNzYWdlPUZBTFNFLCB3YXJuaW5nPUZBTFNFICwgZWNobz1GLCBpbmNsdWRlPUZBTFNFfQ0KcG5nKCJhcnRlMi5wbmciKQ0KDQpzZXEoLTE1LCAxNSwgYnkgPSAwLjA1KSAlPiUNCmV4cGFuZC5ncmlkKHg9LiwgeT0uKSAlPiUNCmdncGxvdChhZXMoeD0oMip4KSwgeT0oc2luaCh4K3kpKzIuOCp4KSkpICsNCmdlb21fcG9pbnQoYWxwaGE9LjEsDQogICAgICAgICAgIHNoYXBlPTIwLA0KY29sb3I9ImFxdWFtYXJpbmU0IiwNCnNpemU9MSkrdGhlbWVfdm9pZCgpKw0KY29vcmRfcG9sYXIoKQ0KDQpkZXYub2ZmKCkNCmBgYA0KDQohW1BpZXphIDI6IHNpbWV0csOtYSBpbnZlcnRpZGFdKGFydGUyLnBuZyl7d2l0aGQ9ODAlfQ0KDQojIyMgUGllemEgMyAtIERpc3RvcnNpw7NuIEdhdXNzaWFuYQ0KDQpMYSBwaWV6YSBkZW5vbWluYWRhIERpc3RvcnNpw7NuIEdhdXNzaWFuYSwgc2UgZ2VuZXLDsyBjb24gYXBveW8gZGUgbGEgZnVuY2nDs24gYG12cm5vcm1gIHBhcmEgcG9kZXIgYXPDrSBjcmVhciBtdWVzdHJhcyBhIHBhcnRpciBkZSBsYSBEaXN0cmlidWNpw7NuIE5vcm1hbCBNdWx0aXZhcmlhZGEgZXNwZWNpZmljYWRhLiBMdWVnbywgcGFyYSBjcmVhciBsYSBmaWd1cmEgc2UgZW1wbGXDsyBgZ2dwbG90MmAuIEVsIHJlc3VsdGFkbyBxdWUgc2Ugb2J0dXZvIGZ1ZSBlbCBzaWd1aWVudGU6DQoNCmBgYHtyIG1lc3NhZ2U9RkFMU0UsIHdhcm5pbmc9RkFMU0UgLCBpbmNsdWRlPUZBTFNFIH0NCiNsaWJyZXJpYXMgcmVxdWVyaWRhcy4NCnJlcXVpcmUodGlkeXZlcnNlKQ0KcmVxdWlyZShnZ3Bsb3QyKQ0KcmVxdWlyZShNQVNTKQ0KcmVxdWlyZShnZ3Zvcm9ub2kpDQoNCnNldC5zZWVkKDEyMzQ1KSAjRmlqYXIgdW5hIHNlbWlsbGEuDQoNClhfMCA8LSBzYW1wbGUoMToxMDAwMCwgc2l6ZSA9IDEwMDApICNNdWVzdHJhIGRlIHRhbWHDsW8gbWlsLg0KeV8wIDwtIHNhbXBsZSgxOjEwMDAwLCBzaXplID0gMTAwMCkgI011ZXN0cmEgZGUgdGFtYcOxbyBtaWwuDQpEYXRhIDwtIGRhdGEuZnJhbWUoeCA9IFhfMCwgeSA9IHlfMCkgI0RhdGEgcXVlIGFsbWFjZW5hIGEgJ3gnIHkgJ3knLg0KDQpYXzEgPC0gbXZybm9ybShuID0gMTUwLCBtdSA9IGMoMCwwLDApLCBTaWdtYSA9IGRpYWcoMykpICNFc3BlY2lmaWNhY2lvbiBkZSBEaXN0IE5vcm1hbCBNdWx0aXZhcmlhZGEuDQp5XzEgPC0gbXZybm9ybShuID0gMTUwLCBtdT01LCBTaWdtYT0gMiwgdG9sID0gMWUtMDYsIGVtcGlyaWNhbCA9IEZBTFNFKSAjT3RyYSBlc3BlY2lmaWNhY2lvbiBkZSBEaXN0IE5vcm1hbCBNdWx0aXZhcmlhZGEuDQoNCk1WTiA8LSBkYXRhLmZyYW1lKHggPSAxMDAgKiBYXzEsIHkgPSAxMDAgKiB5XzEsIGdydXBvID0gcmVwKDEsIDMwMDApKSAjRGF0YSBhc29jaWFkYSBhIGxhcyBlc3BlY2lmaWNhY2lvbmVzIGFudGVyaW9yZXMgeSBnZW5lcmFuZG8gMSByZXBsaWNhIGNhZGEgMzAwMCB2ZWNlcy4NCg0KI1NlIHByb2NlZGUgYSBncmFmaWNhcjoNCnBuZygiYXJ0ZTMucG5nIikNCg0KZ2dwbG90KERhdGEsIGFlcyh4PVhfMCwgeT15XzAsKSkgKw0KICBnZW9tX3Zvcm9ub2kob3V0bGluZSA9IE1WTiwNCiAgICAgICAgICAgICAgIGNvbG9yID0gNSwgc2l6ZSA9IDAuMSkgKw0KICB0aGVtZV92b2lkKCkgKw0KICBjb29yZF9wb2xhcigpICNHZW5lcmFuZG8gZ3JhZmljbyBhcG95YWRvIGRlIHVuYSBkaXN0cmlidWNpb24gZGUgcHJvYmFiaWxpZGFkIG5vcm1hbCBtdWx0aXZhcmlhZGEuDQoNCmRldi5vZmYoKQ0KYGBgDQoNCiFbUGllemEgMzogRGlzdG9yc2nDs24gR2F1c3NpYW5hXShhcnRlMy5wbmcpe3dpdGhkPTgwJX0NCg0KIyMjIFBpZXphIDQgLSBMYSBOb3JtYWxpZGFkIGRlIEJlc3NlbA0KDQpDb24gYXBveW8gZGUgbGEgZnVuY2nDs24gYEJlc3NlbGAgeSBgcmxub3JtYCBzZSBkaXNlw7HDsyBlc3RhIHBpZXphLiBFcyBkZWNpciwgbGEgZmlndXJhIHRpZW5lIHN1IGJhc2UgZW4gdW5hIGNvbWJpbmFjacOzbiBlbnRyZSBsYXMgZnVuY2lvbmVzIGRlIEJlc3NlbCB5IGxhIERpc3RyaWJ1Y2nDs24gTG9nbm9ybWFsIE11bHRpdmFyaWFkYS4gQSBjb25zZWN1ZW5jaWEgZGUgZGljaGEgdW5pw7NuIHNlIG9idHV2byBsYSBzaWd1aWVudGUgb2JyYSBkZSBhcnRlOiANCg0KYGBge3IgbWVzc2FnZT1GQUxTRSwgd2FybmluZz1GQUxTRSAsIGluY2x1ZGU9RkFMU0UgfQ0KI1BhcXVldGUgcmVxdWVyaWRvDQpyZXF1aXJlKEJlc3NlbCkNCg0Kc2V0LnNlZWQoMTIzNDU2Nzg5MCkgI1NlIGZpamEgdW5hIHNlbWlsbGENCg0KeF9tIDwtIHNhbXBsZSgxOjUwMDAsIHNpemUgPSAyMDAwKSNNdWVzdHJhIGRlIHRhbWHDsW8gZG9zIG1pbA0KeV9tIDwtIHNhbXBsZSgxOjUwMDAsIHNpemUgPSAyMDAwKSNNdWVzdHJhIGRlIHRhbWHDsW8gZG9zIG1pbA0KRGF0YV9tIDwtIGRhdGEuZnJhbWUoeF9tLCB5X20pDQoNCnhfbG5vcm0gPC0gc29ydChyb3VuZChybG5vcm0oMTAwMCksIDIpKSAjRGlzdCBsb2cgbm9ybWFsIG11bHRpdmFyaWFkYS4NCnlfQmVzc2VsIDwtIGNiaW5kKHhfbG5vcm0sIGEgPSBiZXNzZWxJKHhfbG5vcm0sIDMpLCBiID0gQmVzc2VsSSh4X2xub3JtLCAzKSkgI0Z1bmNpb25lcyBkZSBCZXNzZWwuDQp4X3kgPC0geF9sbm9ybSArIHlfQmVzc2VsI1NlIGFsbWFjZW5hIGxvIHJlYWxpemFkbyBlbiBlbCBwYXNvIGFudGVyaW9yIGVuIGVzdGEgbnVldmEgdmFyaWFibGUNCg0KI1NlIHByb2NlZGUgYSBncmFmaWNhciBjb24gYXBveW8gZGUgZ2dwbG90MjoNCnBuZygiYXJ0ZTQucG5nIikNCg0KZ2dwbG90KERhdGFfbSwgYWVzKHg9eF9tLCB5PXlfbSkpICsNCiAgICBnZW9tX3Zvcm9ub2kob3V0bGluZSA9IHhfeSwNCiAgICAgICAgICAgICAgIGNvbG9yID0iI0NEMEJCQyIsIHNpemUgPSAwLjAwNSkrIA0KICBnZW9tX3BvaW50KHNpemU9MC41LHN0cm9rZT0xLCBzaGFwZT0yMSxjb2xvcj0iI0NEMEJCQyIpKyANCiAgdGhlbWVfdm9pZCgpICsgY29vcmRfZml4ZWQoKSNHZW5lcmFuZG8gZ3JhZmljbyBhcG95YWRvIGRlIHVuYSBkaXN0cmlidWNpb24gbG9nIG5vcm1hbCBtdWx0aXZhcmlhZGEgeSAgZGUgbGFzIEZ1bmNpb25lcyBkZSBCZXNzZWwuDQoNCmRldi5vZmYoKQ0KYGBgDQoNCiFbUGllemEgNDogTGEgTm9ybWFsaWRhZCBkZSBCZXNzZWxdKGFydGU0LnBuZyl7d2l0aGQ9ODAlfQ0KDQojIyMgUGllemEgNSAtIFJhaW5ib3cuDQoNCkxhIHBpZXphIGRlbm9taW5hZGEgUmFpbmJvdywgc2UgZ2VuZXLDsyBjb24gYXBveW8gZGVkYXRvcyBub3JtYWxlcyBwYXJhIHBvZGVyIGFzw60gY3JlYXIgbXVlc3RyYXMgYSBwYXJ0aXIgZGUgcmVnaXN0cm9zIGxvcyBjdWFsZXMgc29uIGHDsW8sIGdydXBvIHkgdmFsb3Jlcy4gTHVlZ28sIHBhcmEgY3JlYXIgbGEgZmlndXJhIHNlIGVtcGxlw7MgYGdncGxvdGAuIEVsIHJlc3VsdGFkbyBxdWUgc2Ugb2J0dXZvIGZ1ZSBlbCBzaWd1aWVudGU6DQoNCmBgYHtyLCBpbmNsdWRlPUZBTFNFfQ0KDQojR2VuZXJhbmRvIGRhdG9zIHBhcmEgZ3JhZmljYXIuDQpzZXQuc2VlZCgxMTUyMikNCmxpYnJhcnkoUkNvbG9yQnJld2VyKQ0Kbmdyb3VwPTUwDQpuYW1lcz1wYXN0ZSgiR18iLHNlcSgxLG5ncm91cCksc2VwPSIiKQ0KREFUPWRhdGEuZnJhbWUoKQ0KDQpmb3IoaSBpbiBzZXEoMTozMCkpew0KICAgIGRhdGE9ZGF0YS5mcmFtZSggbWF0cml4KDAsIG5ncm91cCAsIDMpKQ0KICAgIGRhdGFbLDFdPWkNCiAgICBkYXRhWywyXT1zYW1wbGUobmFtZXMsIG5yb3coZGF0YSkpDQogICAgZGF0YVssM109cHJvcC50YWJsZShzYW1wbGUoIGMocmVwKDAsMTAwKSxjKDE6bmdyb3VwKSkgLG5yb3coZGF0YSkpKQ0KICAgIERBVD1yYmluZChEQVQsZGF0YSkNCiAgICB9DQpjb2xuYW1lcyhEQVQpPWMoIlllYXIiLCJHcm91cCIsIlZhbHVlIikNCkRBVD1EQVRbb3JkZXIoIERBVCRZZWFyLCBEQVQkR3JvdXApICwgXQ0KDQoNCmNvdWwgPSBicmV3ZXIucGFsKDEyLCAiUGFpcmVkIikgDQpjb3VsID0gY29sb3JSYW1wUGFsZXR0ZShjb3VsKShuZ3JvdXApDQpjb3VsPWNvdWxbc2FtcGxlKGMoMTpsZW5ndGgoY291bCkpICwgc2l6ZT1sZW5ndGgoY291bCkgKSBdDQpgYGANCg0KYGBge3IsIGluY2x1ZGU9RkFMU0V9DQojR3JhZmljYQ0KcG5nKCJhcnRlNS5wbmciKQ0KDQpnZ3Bsb3QoREFULCBhZXMoeD1ZZWFyLCB5PVZhbHVlLCBmaWxsPUdyb3VwICkpICsgDQogICAgZ2VvbV9hcmVhKGFscGhhPTEgICkrDQogICAgdGhlbWVfYncoKSArDQogICAgI3NjYWxlX2ZpbGxfYnJld2VyKGNvbG91cj0icmVkIiwgYnJlYWtzPXJldihsZXZlbHMoREFUJEdyb3VwKSkpKw0KICAgIHNjYWxlX2ZpbGxfbWFudWFsKHZhbHVlcyA9IGNvdWwpKw0KICAgICB0aGVtZSgNCiAgICAgICAgdGV4dCA9IGVsZW1lbnRfYmxhbmsoKSwNCiAgICAgICAgbGluZSA9IGVsZW1lbnRfYmxhbmsoKSwNCiAgICAgICAgdGl0bGUgPSBlbGVtZW50X2JsYW5rKCksDQogICAgICAgIGxlZ2VuZC5wb3NpdGlvbj0ibm9uZSIsDQogICAgICAgIHBhbmVsLmJvcmRlciA9IGVsZW1lbnRfYmxhbmsoKSwNCiAgICAgICAgcGFuZWwuYmFja2dyb3VuZCA9IGVsZW1lbnRfYmxhbmsoKSkNCg0KZGV2Lm9mZigpDQpgYGANCg0KIVtQaWV6YSA1OiBSYWluYm93XShhcnRlNS5wbmcpe3dpdGhkPTgwJX0NCg0KIyMjIFBpZXphIDYgLSBHYW1tYSBCaWcgQmFuZw0KDQpMYSBwaWV6YSBkZW5vbWluYWRhIEdhbW1hIEJpZyBCYW5nLCBzZSBnZW5lcsOzIGNvbiBhcG95byBkZSBsYSBmdW5jacOzbiBgcmdhbW1hYCBwYXJhIHBvZGVyIGFzw60gY3JlYXIgbXVlc3RyYXMgYWxlYXRvcmlhcyBhIHBhcnRpciBkZSBsYSBEaXN0cmlidWNpw7NuIEdhbW1hIGVzcGVjaWZpY2FkYS4gTHVlZ28sIHBhcmEgY3JlYXIgbGEgZmlndXJhIHNlIGVtcGxlw7MgZWwgZGV2dG9vbHNgZGpuYXZhcnJvL2phc21pbmVzYC4gRWwgcmVzdWx0YWRvIHF1ZSBzZSBvYnR1dm8gZnVlIGVsIHNpZ3VpZW50ZToNCg0KYGBge3IsIGluY2x1ZGU9RkFMU0V9DQojUGFxdWV0ZSByZXF1ZXJpZG9zDQojaW5zdGFsbC5wYWNrYWdlcygic2NpY28iKSAgICAgDQojaW5zdGFsbC5wYWNrYWdlcygiVFNQIikgICAgIA0KI2RldnRvb2xzOjppbnN0YWxsX2dpdGh1YigiZGpuYXZhcnJvL2phc21pbmVzIikgICAgICAgICAgIA0KDQpsaWJyYXJ5KGdncGxvdDIpDQpsaWJyYXJ5KGRwbHlyKQ0KbGlicmFyeShzY2ljbykNCmxpYnJhcnkoVFNQKQ0KbGlicmFyeSh0aWR5dmVyc2UpDQpsaWJyYXJ5KGphc21pbmVzKQ0KDQpwbmcoImFydGU2LnBuZyIpDQoNCnVzZV9zZWVkKDExNTIyKSAlPiUNCiAgc2NlbmVfZGlzY3MoDQogICAgcmluZ3MgPSAyMCwgDQogICAgcG9pbnRzID0gcmdhbW1hKDMsIDEsMSkqMTAwMCwgDQogICAgc2l6ZSA9IDUNCiAgKSAlPiUNCiAgbXV0YXRlKGluZCA9IDE6bigpKSAlPiUNCiAgdW5mb2xkX3dhcnAoDQogICAgaXRlcmF0aW9ucyA9IDIsDQogICAgc2NhbGUgPSAwLjUsIA0KICAgIG91dHB1dCA9ICJsYXllciIgDQogICkgJT4lDQogIHVuZm9sZF90ZW1wZXN0KA0KICAgIGl0ZXJhdGlvbnMgPSAyMCwNCiAgICBzY2FsZSA9IDAuMDENCiAgKSAlPiUNCiAgc3R5bGVfcmliYm9uKA0KICAgIHBhbGV0dGUgPSBwYWxldHRlX25hbWVkKCJwbGFzbWEiKSwNCiAgICBjb2xvdXIgPSAiaW5kIiwNCiAgICBhbHBoYSA9IGMoMC4xLCAwLjEpLA0KICAgIGJhY2tncm91bmQgPSAiI0ZCRTVFMjQwIg0KICApDQoNCmRldi5vZmYoKQ0KDQpgYGANCg0KIVtQaWV6YSA2OiBHYW1tYSBCaWcgQmFuZ10oYXJ0ZTYucG5nKXt3aXRoZD04MCV9DQoNCiMjIyBQaWV6YSA3IC0gVG9ybmFkbw0KDQpMYSBzaWd1aWVudGUgcGllemEsIHNlIGNyZWEgYSBwYXJ0aXIgZGVsIGV4cGVyaW1lbnRvIHRvcm5hZG8gZGUgU3RhckNpcmNsZSwgY3JlYW5kbyB1biBhc3BlY3RvIHRyaWRpbWVuc2lvbmFsLCBjYXNpIGVzZsOpcmljbyAoS3VtYXIsIDIwMjApLiBFbCB0b3JuYWRvIHByZXNlbnRhIHBlcXVlw7FhcyBtb2RpZmljYWNpb25lcyBwYXJhIGVzdGFyIG3DoXMgY2VycmFkbywgYXVtZW50YW5kbyBzdSBzZWN1ZW5jaWEsIGNhbWJpYW5kbyBsYSBmdW5jacOzbiBgKGNvcyh5K3gpKzEuMyp5KWAgcG9yIGAoY29zKHkreCkrMTAqeSlgIGVuIGVsIGVqZSBYIHkgYChzaW4oeCt5KSsyLjMqeClgIHBvciBgKHNpbih4K3kpKzAuMSp4KWAgZW4gZWwgZWplIFkuIE51ZXZhbWVudGUgc2UgaGFjZSB1c29zIGRlICBgZ2dwbG90MmAgbGxlZ2FuZG8gYSBlc3RhIGZpZ3VyYS4NCg0KYGBge3IsIGluY2x1ZGU9RkFMU0V9DQpwbmcoImFydGU3LnBuZyIpIA0KDQojc2VxKC0xMiwgMTIsIGJ5ID0gMC4xKSAlPiUNCiNleHBhbmQuZ3JpZCh4PS4sIHk9LikgJT4lDQojZ2dwbG90KGFlcyh4PShjb3MoeSt4KSsxLjMqeSksIHk9KHNpbih4K3kpKzIuMyp4KSkpICsNCiNnZW9tX3BvaW50KGFscGhhPS4wNSwNCiMgICAgICAgICAgIHNoYXBlPTIwLA0KI2NvbG9yPSJyZWQiLA0KI3NpemU9MSkrdGhlbWVfdm9pZCgpKw0KI2Nvb3JkX3BvbGFyKCkNCg0Kc2VxKC0yMCwgMjAsIGJ5ID0gMC4xKSAlPiUNCmV4cGFuZC5ncmlkKHg9LiwgeT0uKSAlPiUNCmdncGxvdChhZXMoeD0oY29zKHkreCkrMTAqeSksIHk9KHNpbih4K3kpKzAuMSp4KSkpICsNCmdlb21fcG9pbnQoYWxwaGE9LjA1LA0KICAgICAgICAgICBzaGFwZT0yMCwNCmNvbG9yPSJyZWQiLA0Kc2l6ZT0xKSt0aGVtZV92b2lkKCkrDQpjb29yZF9wb2xhcigpDQoNCmRldi5vZmYoKQ0KYGBgDQoNCiFbUGllemEgNzogVG9ybmFkb10oYXJ0ZTcucG5nKXt3aXRoZD04MCV9DQoNCiMjIyBQaWV6YSA4IC0gQ2FzdWFsaWRhZA0KDQpMYSBzaWd1aWVudGUgcGllemEsIHNlIGNyZWEgYSBwYXJ0aXIgZGUgbG9zIGRhdG9zIFggeSBZIGRlIGxhIHBpZXphIDMsIERpc3RvcnNpw7NuIEdhdXNzaWFuYSwgcmVhbGl6YW5kbyB0b2RhcyBsYXMgY29tYmluYWNpb25lcyBwb3NpYmxlcyBlbnRyZSBsb3MgZG9zIGZhY3RvcmVzIGNvbiBsYSBmdW5jacOzbiBgZXhwYW5kLmdyaWQoKWAgeSBsYSBmdW5jacOzbiBgKGNvcyh5K3gpKzEuMyp5KWAgZW4gZWwgZWplIFggeSBgKHNpbih4K3kpKzIuMyp4KWAgZW4gZWwgZWplIFkuIERhbmRvIGNvbW8gcmVzdWx0YWRvIGxhIHNpZ3VpZW50ZSBmaWd1cmEuDQoNCmBgYHtyLCBpbmNsdWRlPUZBTFNFfQ0KcG5nKCJhcnRlOC5wbmciKQ0KDQpleHBhbmQuZ3JpZCh4PVhfMSwgeT15XzEpICU+JQ0KZ2dwbG90KGFlcyh4PShjb3MoeSt4KSsxLjMqeSksIHk9KHNpbih4K3kpKzIuMyp4KSkpICsNCmdlb21fcG9pbnQoYWxwaGE9LjA1LA0KICAgICAgICAgICBzaGFwZT0yMCwNCmNvbG9yPSJyZWQiLA0Kc2l6ZT0xKSt0aGVtZV92b2lkKCkrDQpjb29yZF9wb2xhcigpDQoNCmRldi5vZmYoKQ0KYGBgDQoNCiFbUGllemEgODogQ2FzdWFsaWRhZF0oYXJ0ZTgucG5nKXt3aXRoZD04MCV9DQoNCiMjIyBQaWV6YSA5IC0gdHJlZV8xDQoNClBhcmEgZWwgdHJlZV8xLnBuZyBzZSBtdWVzdHJhIHVuYSBncmFmaWNhIGNyZWFkYSBhIHBhcnRpciBkZSByYW5kb20gZm9yZXN0IGdlbmVyYWRvIGNvbiB1biBncmFuIGRhdGFzZXQgZGUgc2tsZWFybiwgZXMgaW50ZXJlc2FudGUgdmVyIGNvbW8gY29uIGxhIGdyYW4gY2FudGlkYWQgZGUgZGF0b3Mgc2FsZW4gbXVjaGFzIHJhbWFzIHF1ZSBwdWVkZW4gcGFyZWNlciB1bmEgZ3JhbmphIGRlIGhvcm1pZ2FzIG8gdW4gZW5vcm1lIMOhcmJvbCBnZW5lYWzDs2dpY28gbyBkZSBldm9sdWNpw7NuLg0KDQohW1BpZXphIDk6IHRyZWVfMV0odHJlZV8xLnBuZyl7d2l0aGQ9ODAlfQ0KDQojIyMgUGllemEgMTAgLSB0cmVlXzINCg0KUGFyYSBlbCB0cmVlXzIucG5nIHNlIG11ZXN0cmEgaWd1YWxtZW50ZSB1bmEgZ3JhZmljYSBnZW5lcmFkYSBjb24gcmFuZG9tIGZvcmVzdCB5IGVsIG1pc21vIGRhdGFzZXQsIGVzIG1lbm9zIGxsYW1hdGl2byB5IGFsIHBhcmVjZXIgbWVub3MgY29tcGxlam8gcGVybyByZWFsbWVudGUgcHVlZGUgdmFyaWFyIG3DoXMgdmlzdWFsbWVudGUsIGxhcyBmb3JtYXMgcXVlIG11ZXN0cmEgcHVlZGVuIHBhcmVjZXJzZSBhIHVuIGNlcmVicm8sIHVuIGVsZWZhbnRlLCB1biBjcsOhbmVvLi4uIGRlcGVuZGUgbGEgcGVyY2VwY2nDs24gZGUgcXVlaW4gbG8gZXN0w6kgdmllbmRvIHkgZGUgY29tbyBzZSBhbGxhIGdlbmVyYWRvIGxhIGltYWdlbiBhbGVhdG9yaWFtZW50ZSwgdG9kb3MgbG9zIHBlcXVlw7FvcyBsZXRyZXJvcyBvIGN1YWRyb3MgZGUgbGEgaW1hZ2VuIHNvbiB2YWxvcmVzIGRlIGxhcyBob2phcyBkZWwgcmFuZG9tIGZvcmVzdCwgbG9zIHZhbG9yZXMgZGVsIGRhdGFzZXQgc29uIGlycmVsZXZhbnRlcyBwYXJhIGxvIHF1ZSBlc3RhbW9zIGhhY2llbmRvLCBzw7NsbyBwdWVkZW4gdmFyaWFyIGVsIGNvbG9yIGRlIGNhZGEgdW5vIGRlIGVzdG9zIGxldHJlcm9zIG5hcmFuamFzLg0KDQohW1BpZXphIDEwOiB0cmVlXzJdKHRyZWVfMi5wbmcpe3dpdGhkPTgwJX0NCg0KDQoNCg0KDQoNCiMjIDMuIENvbmNsdXNpb25lcw0KDQotIExhcyBwaWV6YXMgYXJ0w61zdGljYXMgY3JlYWRhcyBwb3IgbWVkaW8gZGUgbGFzIHTDqWNuaWNhcyBhZmlhbnphZGFzIGVuIGVsIGN1cnNvIHNvbiB1bmEgbXVlc3RyYSBkZSBsbyBiZWxsbyBxdWUgZXMgbGEgQ2llbmNpYS4gRXMgZGVjaXIsIG5vIHNvbGFtZW50ZSBhcGxpY2FyIG3DqXRvZG9zIG1hdGVtw6F0aWNvcyB5IGVzdGFkw61zdGljb3MgcGFyYSBzb2x1Y2lvbmFyIHByb2JsZW1hcyBkZSBsYSBjb3RpZGlhbmlkYWQsIHNpbm8gYWhvcmEgcGFyYSBoYWNlciBkZSBlbGxvIGFsZ28gbcOhcyB0YW5naWJsZSwgcHJveWVjdGFkbyBlbiB1bmEgc2VyaWUgZGUgaW3DoWdlbmVzLCBwYXJhIHF1ZSBzZSBwdWVkYSBhcHJlY2lhciB0YW1iacOpbiBwb3IgcGVyc29uYXMgcXVlIG5vIG5lY2VzYXJpYW1lbnRlIGVzdMOhbiBpbm1lcnNhcyBlbiBlc3RlIG11bmRvIGxhcyBjaWVuY2lhcyBmb3JtYWxlcy4NCg0KLSBGdWUgdW4gZXhjZWxlbnRlIHJldG8gaGFjZXIgZXN0ZSBwcm95ZWN0bywgeWEgcXVlIG5pbmd1bm8gZXN0YWJhIGZhbWlsaWFyaXphZG8gY29uIGVsIGNvbmNlcHRvIGRlICJBcnRlIEdlbmVyYXRpdm8iLiBBZGVtw6FzLCBjb25zaWRlcmFuZG8gcXVlIHNlIGVzdMOhIGN1bG1pbmFuZG8gZWwgcGVyw61vZG8gYWNhZMOpbWljbyBzaXJ2acOzIGRlIHRlcmFwaWEgYW50aWVzdHLDqXMgcmVhbGl6YXIgY2FkYSBmaWd1cmEuDQoNCi0gTGFzIHBpZXphcyBxdWUgc2UgZ2VuZXJhcm9uIHBhcmEgZXN0ZSB0cmFiYWpvIHZhbiBkZXNkZSBtZXRvZG9sb2fDrWFzIGNvbW8gInJhbmRvbSBmb3Jlc3QiLCBoYXN0YSAiZnVuY2lvbmVzIGRlIEJlc3NlbCIsIGxvIGN1YWwgaW1wbGljYSBxdWUgc2UgcHJvcG9yY2lvbsOzIGdyYW4gdmFyaWVkYWQgZGUgY29udGVuaWRvIHkgaGFjZSBxdWUgaW1wbMOtY2l0YW1lbnRlIHNlIG5vdGUgbGEgc2VyaWVkYWQgeSBjb21wcm9taXNvIGNvbiBlbCBxdWUgc2UgdG9tw7MgZWwgw7psdGltbyB0cmFiYWpvIHBhcmEgZGljaG8gY3Vyc28uDQoNCg0KDQoNCg0KDQojIyA0LiBFbmxhY2VzIGRlIGludGVyw6lzDQoNCg0KVXN0ZWQgcHVlZGUgcmV2aXNhciBlbCBjw7NkaWdvIHkgbG9zIGRhdG9zIHVzYWRvcyBlbiBlc3RlIHByb3llY3RvIGVuIG51ZXN0cm8gcmVwb3NpdG9yaW8gZW4gW0dpdGh1Yl0oaHR0cHM6Ly9naXRodWIuY29tL2RhYXRvcm9hZy9QUk9ZRUNUT1MtVEFFL3RyZWUvbWFpbi9DdWFydGElMjBlbnRyZWdhKQ0KDQojIyA1LiBSZWZlcmVuY2lhcw0KDQorIFVyZ2lsZXMsIEouICgyMiBkZSBub3ZpZW1icmUgZGUgMjAxOSkuICpFbCBhcnRlIGdlbmVyYXRpdm8sIGVudHJlIGxhIGNpZW5jaWEgY29tcHV0YWNpb25hbCB5IGxhIGNyZWF0aXZpZGFkIGFydMOtc3RpY2EuIFVjdWVuY2EuIE9idGVuaWRvIGRlIGh0dHBzOi8vd3d3LnVjdWVuY2EuZWR1LmVjL2NvbXBvbmVudC9jb250ZW50L2FydGljbGUvMjMzLWVzcGFub2wvaW52ZXN0aWdhY2lvbi9ibG9nLWRlLWNpZW5jaWEvMTM4Ny1hcnRlLWpvc2UtdXJnaWxlcz9JdGVtaWQ9NDM3Kg0KDQorIEt1bWFyLCBTLiAoMjcgZGUgbWF5byBkZSAyMDIwKS4gKkFkdmFuY2VkIEFuYWx5dGljcywgTWFjaGluZSBMZWFybmluZywgQXJ0aWZpY2lhbCBJbnRlbGxpZ2VuY2U6IEV4cGVyaW1lbnRzIGluIEdlbmVyYXRpdmUgQXJ0IFdpdGggUlN0YXRzLiBBQU1MQUkgT2J0ZW5pZG8gZGUgaHR0cHM6Ly93d3cuYWFtbGFpLmNvbS8yMDIwLzA1LzI3L2V4cGVyaW1lbnRzLWluLWdlbmVyYXRpdmUtYXJ0LXdpdGgtcnN0YXRzLyoNCg0K