הורדת שירים לאייפון מיוטיוב
ויאגרה 100 מ"ג שימוש
תרגום אנגלית לעברית בחינם
рейтинг брокеров бинарных опционов 2016
קמגרה גל
алекс экспрес

Author Archives: Emiliano - Page 2

Este año voy a…

escribir más por acá.

mafalda-escritora

Me gusta escribir por este lugar, me divierte pero a la vez me frustra. La cantidad de escritos desechados por disconformidad literaria me abruma. En estas épocas donde el parecer le lleva varias cabezas al ser, presiento las miradas insidiosas de los azarosos naufragantes en la nuca (se nota que es irónico, no?), lo que me inhibe a expresar mis ideas, códigos -que es lo mismo-, implementaciones geekys, y delirios místicos. Eso, querido lector estocástico, hasta hoy!!

Ahora voy a mejorar mi perfil escupidor a la web a través de este humilde blog. Entonces, para ser organizado me voy a poner un umbral mínimo mensual, y cumpliendo eso ya me voy a sentir satisfecho, así que para este año tengo tareas de dimensiones bíblicas,  además de conquistar a Natalia Oreiro pretendo tener al menos dos publicaciones por mes, con lo cual, a las 23.59 hs del 31 de diciembre tendré que haber cumplido con este reto, sino, definitivamente -y acá viene lo bravo y diabólico- no pasará absolutamente nada, claro, a quién carajo le afecta!

Ya avisé, ya me avisé.

Los 24 de Marzo

 

Me preguntaba cómo habrán sido las tapas de los diarios argentinos a lo largo de la historia para los 24 de marzo, por supuesto desde 1976 al día de la fecha.

Como ya había estado descargando anteriormente todas las tapas de la mayor corporación mediática de Argentina con serios tintes mafiosos, me dije, “vamos a compararlos con otros”.

Sería interesante ver qué publicaban en tapa y contrastar a Página 12, Clarin y La Nación.

Acá me encontré con una serie de complicaciones que no esperaba. Primero, lo único que tenía resuelto antes de arrancar ya no funcionaba, el gran diario argentino había cambiado el modo de acceder a sus tapas, con lo cuál tenía que empezar de cero.

Lamentablemente el diario conservador y ultra-católico de los Mitre no publica un registro de sus tapas, al menos, luego de haber recorrido su sitio web no pude encontrarlas.

Por lo tanto me quedaba ver si el Página 12 tenía un modo de acceder a sus tapas y ya olfateaba que esto iba a ser poco menos que un parto. Por suerte logré encontrar cómo acceder a las imágenes, sin embargo es un diario bastante nuevo comprarado con los otros, existe desde 1987, y el acceso a sus tapas data desde el 1998.

Entonces, hagamos lo que se puede, vamos a comparar las tapas de cada 24 de Marzo desde 1998 a 2013, ya que clarín no permite el acceso a la última tapa, aunque supongo que la mayoría intuirá la relevancia que tuvo en la portada este nuevo aniversario del golpe de estado.

La solución a este breve desafío se puede resumir en lo siguiente:

  • Descargar las tapas de cada uno de los diarios en el rango de fechas.
  • Acomodar el tamaño para que sean parecidos, lo mejor posible, porque tampoco siempre tienen el mismo tamaño.
  • Unir las dos tapas en una imagen.

Para resolver el primer item tuve que analizar en cada sitio web cuál es el patrón de las URLs para acceder a las tapas. En clarín es muy fácil el acceso, la url que hay que armar es la siguiente:

http://tapas.clarin.com/tapa/2013/03/24/20130324_thumb.jpg

Donde la fecha hay que armarla haciendo y + “/” + m + “/” + d + “/” + y + m + d, y finalmente concatenarla a “http://tapas.clarin.com/tapa/” y agregándole al final “_thumb.jpg”.

En Página el acceso a las tapas es un verdadero lío, sobretodo en los primeros años de su creación. El nombre de archivo no es siempre el mismo, varían anárquicamente entre: tapan.jpg, Tapan.jpg , TAPAN.JPG, tapagn.jpg y TAPAGN.JPG. Además de esto, a veces se almacenan en

http://www.pagina12.com.ar/fotos/”+fecha+”/diario/”+filename

donde fecha es algo así: y + “/” + y[2] + y[3] +”-“+ m +”/”+ y[2] + y[3] +”-“+ m +”-“+ d

Y otras veces están en http://www.pagina12.com.ar/”+fecha+”/”+filename donde fecha es y+m+d.

Entonces, todo esto en un script python en el que para resolver esta última anarquía comento a manopla las urls, fecha y filename donde buscar (ejemplo 1 y ejemplo 2 en el código).

from urllib2 import Request, urlopen, URLError, HTTPError

def get_tapa(diario,file_mode,y,m,d):

    if diario == "clarin":
        # Armo la url de clarin
        fecha = y + "/" + m + "/" + d + "/" + y + m + d
        filename = "_thumb.jpg"
        url = "http://tapas.clarin.com/tapa/"+fecha+filename
    elif diario == "pagina12":
        # Armo las urls de pagina12

        # 1 - Ejemplo: http://www.pagina12.com.ar/2000/00-03/00-03-24/tapan.jpg
        fecha = y + "/" + y[2] + y[3] +"-"+ m +"/"+ y[2] + y[3] +"-"+ m +"-"+ d
        filename = "tapan.jpg"
        url = "http://www.pagina12.com.ar/"+fecha+"/"+filename

        # 2 - Ejemplo: http://www.pagina12.com.ar/fotos/20130324/diario/
        # El filename puede ser:
        #                tapan.jpg Tapan.jpg TAPAN.JPG
        #                tapagn.jpg TAPAGN.JPG
        #filename = "TAPAGN.JPG"
        #fecha = y+m+d
        #url = "http://www.pagina12.com.ar/fotos/"+fecha+"/diario/"+filename

    # Hago el request
    req = Request(url)

    try:
        # Abro url
        f = urlopen(req)
        print "downloading " + url

        # Armo el nombre de archivo usando la fecha y el filename
        local_file = open("tapas_24Marzo/"+diario+"/"+diario+ y +"-"+ m +"-"+ d +"-"+filename[:-4]+".jpg", "w" + file_mode)

        # Escribo el archivo localmente
        local_file.write(f.read())
        local_file.close()		

    # handle errors
    except HTTPError, e:
        print "HTTP Error:",e.code , url

    except URLError, e:
        print "URL Error:",e.reason , url

if __name__ == "__main__":

    print "starting..."

    # Fecha inicio y final
    y,m,d = "1974", "03", "24"
    y_fin = "2014"

    # Itero entre el intervalo
    for a_year in range(int(y),int(y_fin)+1):
    	get_tapa("clarin","b",str(a_year),m,d)
    	get_tapa("pagina12","b",str(a_year),m,d)

Las imágenes, como era de esperar tienen diferente tamaño y no siempre el mismo, las de clarín son un poco más de el doble. Así que voy a hacer un script en bash usando imagemagick para redimensionar todas imágenes a un 45% de su tamaño original. Sería:

#!/bin/bash

for i in $(ls tapas_24Marzo/clarin/*.jpg)
do
	convert $i -resize 45% tapas_24Marzo/clarin/half/${i:21}
	#echo tapas_24Marzo/clarin/half/${i:21}
done

Ahora queda hacer otro script para unir en una imagen las dos tapas. Esto no lo generalizo porque no le puse un mismo nombre de archivo a los de Página, tuve la mala idea de dejarle el nombre original, que como les decía es un caos. Sin embargo, es una tarea que no reviste mayor complejidad para hacerlo manualmente:

convert +append clarin2013-03-24.jpg pagina122013-03-24-tapan.jpg 2013-03-24_clarin-pagina12.jpg

Al inicio del post está el álbum comparativo, pero ya que estamos muestro las tapas de clarin de los 24 de Marzo desde 1974 al 2013, salvo algunas que sospechosamente no son accesibles. Estas son:

 

Cualquier análisis sobre el contenido, por mencionar alguno, en 1976 se tituló “NUEVO GOBIERNO”, lo dejo para charlas personales. Por último, me encanta la pluma de José Pablo Feinmann, y me encontré con un artículo en la contratapa del Página de 2001 que les recomiendo.

Desde lejos no se ve

linux-python-logo

Hermoso domingo soleado, ideal para preparar unos mates con yerba mbopicua escuchar un random de algún CD de Las Pelotas y ponerse a programar ese problema que tanto te quita el sueño, que te hace caminar cabizbajo, con la mirada perdida y un peso inaguantable sobre las espaldas, donde cada paso dado sin resolverlo pesa más y más.

¿Cuál es mi problema?

No plasmar lo que imagino en mi cabeza en la cancha de fútbol, ese el drama de mi vida. También este otro:

Una PC instalada en campo -a 80 km de Santa Fe-, conectada a Internet mediante un enlace wifi de una escuela rural, se enciende en forma automática todas las noches todas y me envía un conjunto de datos sobre el estado de ciertas variables hidrológicas – ambientales. Resulta ser que venía todo perfecto por casi 2 meses hasta que nunca más se encendió. El auto-encendido se realizaba mediante la configuración de la BIOS, con lo cuál me es imposible resolverlo remotamente.

A sabiendas que no es un problema de alimentación, que no se quemó nada, debo suponer que por alguna razón que desconozco a la REP**ISIMA BIOS se le desconfiguró la opción de auto-encendido. Entonces mi solución viene dada por prenderla en forma remota usando el protocolo Wake On Lan (WOL). Ahora bien, ese Lan quiere decir eso, que tiene que ser desde la LAN, no desde Internet, donde estoy yo.

Por suerte, dejé en la escuela, un pequeño router de $150 con una versión de GNU/Linux embebido corriendo (openwrt) que forma parte de una VPN a la que puedo acceder desde donde sea si tengo mi notebook en mis manos. Una opción sería programar en el cron de este router que todos los días a una determinada hora envíe usando el WOL la señal de auto-encendido a la PC en el campo.

Eso andaría perfecto si el router tendría un reloj interno, entonces las 23hs del router son las 23hs del resto de Argentina, pero no es así, no lo tiene y atrasa más que TN. Entonces, qué carajo hago? Bueno,  puedo conectarme desde un servidor público a través de la VPN y mandarle a ejecutar un script que a su vez es el que le manda ese paquete mágico a través de la LAN a la PC en campo para que se prenda. Una vez que se enciende estamos todos felices y contentos.

Lo único que quisiera es que esto último se haga solo y no tenga que estar YO ejecutándolo. Entonces necesito hacer un programa que desde el servidor se conecte al router a las 23hs e interactúe ejecutando un script que haga lo que dije antes que tiene que hacer.

La receta lleva los 2 ingredientes siguientes:

  • Python
  • El módulo pyexpect

Usando pyexpect voy a conectarme desde el servidor usando ssh, y luego ejecuto el script getUP.sh, además todo lo que va pasando lo logueo. Lo hago así:

import pxssh
import logging

def main(logfilename, hostname, username, password, command, port='22'):
    logging.basicConfig(filename=logfilename,
         format='%(asctime)s - %(levelname)s - %(message)s', level=logging.DEBUG)

    try:
        s = pxssh.pxssh()
        s.login (hostname, username, password, port=port)
        logging.info(hostname+": login successfully" )

        s.sendline(command)
        logging.info(hostname + ' -> ' + command + ": command sent successfully")

        s.prompt()
        logging.info(hostname + ' -> ' + command + " has returned: "+s.before)
        s.logout()

    except pxssh.ExceptionPxssh, e:
        logging.error("pxssh failed: " + str(e))

if __name__ == "__main__":
    logfilename = 'logGetUpNC.log'
    hostname = '192.168.111.94'
    command = './getUP.sh'
    username = 'root'
    password = 'aca va la password'
    main(logfilename, hostname, username, password, command)

Como verán es muy simple el programa desarrollado, usé pxssh que es parte de pyexpect. Ahora, el script que está en el router con openwrt hace eso de mandar por la LAN el paquete mágico de encendido, utilizando el programa para tal fin llamado etherwake:

#!/bin/sh
etherwake -D -i br-lan 00:1C:C0:A7:F7:2D

Sí, ya se lo que estás pensando: ¿Por qué no actualizo regularmente la hora del router usando NTP y desde ahí lo enciendo cuando quiero, incluso si no hay Internet podés hacer tu autoencendido?

Qué querés que te diga, tenés razón, pero a esto ya lo sabía hacer y lo que acabo de escribir no, los domingo están hechos para aprender algo nuevo, no para repetir lo ya conocido. Tamos?

 

 

Titi 0.1.0 is out!

Estoy empezando a escupir mi código a la web. Y el primer escupitajo tiene que ver con un software hecho en dos fines de semana de noches mas que largas, se llama Titi y de acá se lo pueden bajar.

¿Qué es Titi?

Es un visualizador de imágenes satelitales o de radar multibanda que soporta una inmensa cantidad de formatos (mas de 100). Además permite extraer (por ahora sólo para imágenes georeferenciadas en la cabecera) valores de la imagen a partir de una latitud y longitud ingresada, así como también obtener el valor de la imagen a partir de un click sobre la misma.

Oficialmente titi es un acrónimo recursivo rebuscado de Titi Is a saTellital Image viewer, pero ciertamente es un homenaje a una de mis abuelas. Acá les muestro un par de capturas de pantalla de titi en acción mostrando imágenes ASTER GDEM v2 (Advanced Spaceborne Thermal Emission and Reflection Radiometer Global Digital Elevation Model Version 2) con diferentes mapas de colores.

titi0.1.1-ncartiti0.1.0

Características

– Soporte para un inmensa cantidad de formatos gracias al uso de Geospacial Data Abstraction Library (GDAL).
– Extracción de valores a partir de una latitud y longitud dada.
– Extracción de valores a partir de clickear sobre el pixel deseado.
– Soporte para diferentes mapas de color.
– Soporte para imágenes multibanda.

 ¿Cómo está hecho?

Obviamente está programado en Python. Para la interfaz gráfica usé WxPython. Para leer las imágenes usé PyRaster que es  wrapper de python-gdal (Python bindings to the Geospatial Data Abstraction Library) que me las devuelve a las imágenes en formato de matrices NumPy, por lo que usé NumPy y finalmente lo visualizo usando la librería gráfica Matplotlib.

Tenía desarrollado para uso propio un visualizador en consola (ShowSatImg), así que me basé en eso y le agregué todas esas pavaditas gráficas usando como base un template de http://www.oneminutepython.com. Como verán soy degenerado a la hora de hacer interfaces gráficas, es más las detesto, pero debo reconocer que para que sea usada por colegas, amigos, etc, hay que escaparle a los scripts en consola.

¿Cómo sigue esta historia?

Voy a reescribirla desde cero, pero así como está ya es funcional, por lo que pueden bajarla y probarla. Hasta ahora hice todo bien a pata, lo que me permitió comprender mejor el tema de las GUI del #$%$, pero ahora pretendo usar algún entorno que me facilite las tareas de diseño.

To Do List

– Soporte para operaciones matemáticas sobre distintas bandas.
– Operaciones matemáticas predefinidas (NDVI, NDWI, etc.).
– Acciones masivas sobre un conjunto de imágenes seleccionadas (recorte, extracción, etc).
– Soporte para georeferenciar imágenes cuya información no se encuentra en la cabecera.
– Visualización 3D usando mayavi.
– …

 

Juego de la vida

Dicta wikipedia: El juego de la vida es el mejor ejemplo de un autómata celular, diseñado por el matemático británico John Horton Conway en 1970.

No se bien por qué me atraen bastante estos jueguitos, debe ser porque (acá viene un razonamiento serio) leí de muchos laburos con los que logran imitar comportamientos muy complejos con reglas realmente simples, tales como la infección de células con HIV en el organismo humano, o la dinámica de un incendio  o también debe ser (y acá viene la boludez) porque ya terminé de ver todas las temporadas de Capusotto.

El tema surge porque hace un par de días un alumno me consultó sobre este ejercicio y lo planteamos medio por arriba, más por lo laborioso que por su complejidad. Así que, para evitar que me atormente la culpa y la angustia, me repartí la siesta del sábado y del domingo para programarlo en Python y, de paso para hacer unas animaciones y comprender mejor el comportamiento de estos bichos. Además, lo plasmo acá debido al incentivo de un ex profesor y ex jefe que a veces lee este estático blog, Gracias Pablo!

Entonces, el juego consiste en un conjunto de bichos vivos o muertos cuyo estado cambia en el tiempo (de generación en generación) dependiendo de lo que haya a su alrededor, es decir, varía en función de su estado (vivo o muerto) y de sus vecinos.

Las reglas de evolución son la siguientes:

  • Una célula muerta con exactamente 3 vecinas vivas => vive
  • Una célula viva con mas de 3 vecinas vivas => muere
  • Una célula viva con 2 o 3 vecinas vivas => vive
  • Una célula viva con menos de 2 vecinas vivas => muere

Desde el punto de vista de su implementación, lo hice del siguiente modo:

  • La población de células es una matriz de mxn, cuyo valor es 1 o 0 (viva o muerta respectivamente) que se inicia en forma aleatoria.
  • Los vecinos son los que están alrededor, donde hay que tener en cuenta que no todos tienen la misma cantidad de vecinos:
  • Las cuatro células de las esquinas tienen 3 vecinos.
  • Las del borde sin contar las esquinas tienen 5.
  • Las del interior están rodeadas, por lo que se debe controlar el estado de las 8 células vecinas.

Entonces, teniendo en cuenta estos detalles e iterando sobre la cantidad de generaciones para observar su evolución nos queda un hermoso código de aproximadamente 100 líneas:

import numpy as np
import matplotlib.pyplot as plt
import scitools.std as sci

def nuevo_estado(celula_viva,vecinos):
    ''' Reglas de evolucion:
        - celula  muerta  con  exactamente 3 vecinas vivas => vive
        - celula viva con mas de 3 vecinas vivas           => muere
        - celula viva con 2 o 3 celulas vecinas vivas      => vive
        - celula viva con menos de 2 vecinas vivas         => muere
    '''
    vive = 1
    muere = 0
    estado = celula_viva.copy()
    vecinas_vivas = sum(vecinos)

    if celula_viva:
        # celula viva => contemplo solo los casos en los que muere
        if vecinas_vivas > 3:
            estado = muere
        elif vecinas_vivas < 2:
            estado = muere
    else:
        # celula muerta
        if vecinas_vivas == 3:
            estado = vive
    return estado

def main(m,n,generaciones):
    # mi semilla
    np.random.seed()

    poblacion = np.random.randint(2,size=(m,n))
    gen_tempo = np.zeros((m,n), int)

    celulas_vivas = []
    celulas_vivas.append(np.sum(poblacion))
    # BW
    plt.imshow(poblacion, cmap='binary', interpolation='nearest')
    # Grey
    #plt.imshow(poblacion, cmap='binary')
    counter = 1
    plt.savefig('img/tmp%04d.png' %counter)
    #plt.show()

    for g in range(1,generaciones+1):
        # ------------------------------
        # Hay 3 casos para especiales:
        # ------------------------------
        # 1- En las esquinas de la matriz

        # -- Superior e infrerior izquierda
        vecinos = np.array([poblacion[0,1], poblacion[1,1], poblacion[1,0]])
        gen_tempo[0,0] = nuevo_estado(poblacion[0,0],vecinos)

        vecinos = np.array([poblacion[m-2,0], poblacion[m-2,1], poblacion[m-1,1]])
        gen_tempo[m-1,0] = nuevo_estado(poblacion[m-1,0],vecinos)

        # -- Superior e inferior derecha
        vecinos = np.array([poblacion[0,n-2], poblacion[1,n-2], poblacion[1,n-1]])
        gen_tempo[0,n-1] = nuevo_estado(poblacion[0,n-1],vecinos)

        vecinos = np.array([poblacion[m-1,n-2], poblacion[m-2,n-2], poblacion[m-2,n-1]])
        gen_tempo[m-1,n-1] = nuevo_estado(poblacion[m-1,n-1],vecinos)

        # 2- En la matriz sin los bordes
        for i in range(1,m-1):
            for j in range(1,n-1):
                vecinos = np.array([poblacion[i-1,j-1],poblacion[i-1,j],poblacion[i-1,j+1,],
                                    poblacion[i,j-1],poblacion[i,j+1],
                                    poblacion[i+1,j-1],poblacion[i+1,j],poblacion[i+1,j+1]])
                gen_tempo[i,j] = nuevo_estado(poblacion[i,j],vecinos)

        # 3- En los 4 bordes sin las esquinas
        for i in range(1,m-1):
            # Columna izquierdo
            vecinos = np.array([poblacion[i-1,0],
                                poblacion[i-1,1],poblacion[i,1],poblacion[i+1,1],
                                poblacion[i+1,0]])
            gen_tempo[i,0] = nuevo_estado(poblacion[i,0],vecinos)
            # Columna derecha
            vecinos = np.array([poblacion[i-1,n-1],
                                poblacion[i-1,n-2],poblacion[i,n-2],poblacion[i+1,n-2],
                                poblacion[i+1,n-1]])
            gen_tempo[i,n-1] = nuevo_estado(poblacion[i,n-1],vecinos)

        for i in range(1,n-1):
            # Fila superior
            vecinos = np.array([poblacion[0,i-1],
                                poblacion[1,i-1],poblacion[1,i],poblacion[1,i+1],
                                poblacion[0,i+1]])
            gen_tempo[0,i] = nuevo_estado(poblacion[0,i],vecinos)
            # Fila inferior
            vecinos = np.array([poblacion[m-1,i-1],
                                poblacion[m-2,i-1],poblacion[m-2,i],poblacion[m-2,i+1],
                                poblacion[m-1,i+1]])
            gen_tempo[m-1,i] = nuevo_estado(poblacion[m-1,i],vecinos)

        poblacion = gen_tempo.copy()
        plt.imshow(poblacion, cmap='binary', interpolation='nearest')
        #plt.imshow(poblacion, cmap='binary')
        plt.savefig('img/tmp%04d.png' %(counter+g))
    sci.movie('img/tmp*.png', output_file='img/juegoDeLaVida_'+str(m)+'x'+str(n)+'_'+str(generaciones)+'gen.gif')

if __name__ == "__main__":
    filas = 100
    columnas = 100
    generaciones = 200
    main(filas,columnas,generaciones)

Y bueno, el gif generado con el código previo, para una población de 100×100 y una evolución de 200 generaciones (me siento Darwin) se puede observar haciendo click sobre la siguiente imagen.

juegoDeLaVida_100x100_200genBW

Para la visualización usé matplotlib, para la animación scitools, y el laburo de arreglos usando numpy. Nada del otro mundo. Solo le faltaría una interfaz gráfica de usuario, con botoncitos, cuadritos, florcitas y esas yerbas, pero la verdad, detesto programarlas, ya subiré el código a un repositorio público (estoy laburando en eso) para que quien quiera lo modifique o sino que lo pida y capaz lo agarro con más ganas.

Por último, recomiendo hacer como ejercicio inicial este juego para aprender a programar, tiene un mix de todo sin alcanzar una complejidad elevada, y además, una vez concluido permite filosofar sobre la evolución de las especies, los límites del universo y por qué no hay canchas de futbol 5 con el nombre de Messi todavía, todo eso con buen vinito de por medio.

A New Kind of Science

Stephen Wolfram - A New Kind Of Science

Ese es el título del afamado libro de Stephen Wolfram cuyo acceso online es gratuito. Hace rato que lo vengo ojeando pero pocas veces me puse a programar algo de lo que desarrollaba. Hasta hoy!

Domingo lluvioso, ideal para programar pequeños fragmentos de código horrible para reproducir los autómatas celulares (AC) que tanto investigó este tipo. La utilidad de los AC son amplias, tienen aplicaciones diversas que van desde las boludeces aquí presentadas hasta comportamientos mucho más complejos como la modelación del crecimiento de un tumor, por mencionar algo. Sin embargo, acá no nos importa todas las demás aplicaciones, al menos no por ahora, sino empezar con los experimentos del capítulo 2 e ir avanzando con lo que plantea el libro.

Los AC pueden definirse como una grilla de células donde sus estados son finitos y pueden evolucionar en función de su estado actual y del estado de sus vecinos. Bueno, eso es una definición mía agarrada de los pelos, en wikipedia está mejor. En criollo sería algo así como: dime como estás y cómo están con los que te juntas y te diré como estarás mañana.

Yendo un poco más específicamente a lo que plantea Estifen en el capítulo 2 de su libro, una célula puede ser negra o blanca (1 o 0 respectivamente), así de fácil. El tema es el conjunto de reglas que se le imponen para cambiar a blanco o a negro. Por ejemplo, si tenemos en un momento determinado 8 células dispuestas linealmente de este modo: 0001000

En el paso siguiente va a haber algunas que cambian de 0 a 1 y viceversa, evaluando su estado y el de sus inmediatas vecinas, es decir la de la izquierda y de la derecha. Acá surge la duda de qué hacemos con la de los extremos, las obviamos, empezamos tomando las tres primeras (000) para ver qué nuevo valor va a tener la central, luego las tres siguientes (001), las otras tres (010) y así sucesivamente hasta tomar las últimas tres células (000) .

De manera tal que los 3 primeros ceros, 000, van a determinar el nuevo valor de la célula del medio. La regla denominada Rule 30, realiza los siguientes cambios:

000: 0
001: 1
010: 1
011: 1
100: 1
101: 0
110: 0
111: 0

El primer caso se explicaría así: cuando la célula central es 0 y las vecinas son 0, entonces el nuevo valor de la célula será 0. Ahora, por qué se llama regla 30? bueno, si te fijás la columna de la derecha forma el número 30 si convertís a decimal el número 00011110, se entiende? ok, así me gusta.

O sea que ya tenemos casi todo. Cómo se hace? Bueno, vamos tomando de a 3 células y hacemos la actualización. Con el valor inicial dado 0001000, se irían actualizando las nuevas generaciones de la siguiente manera:

 

0011100
0110010
0101110

Con estas reglas tan simples se generan estructuras complejas como las de acá:

rule30-zoomrule73-145x120-zoomrule146-zoom rule150-zoom

El código necesario para generar estas y otras figuras está hecho en Python. Las generaciones serían la cantidad de filas de la imagen, y las reglas van desde 0 hasta 255 generando una figura pbm por cada una.

import ACfunctions as ac
gen=10
for rule in range(256):
    bit_ini='00000100000'
    header = 'P1 '+ str(len(bit_ini)) + ' '+str(gen)
    o = open("rule"+str(rule)+"-"+str(len(bit_ini)) + 'x'+str(gen)+".pbm",'w')

    o.write(header+"\n")
    o.write(bit_ini+"\n")

    new_bit='0'
    for n in range(gen):
        for i in range(len(bit_ini)-2):
            new_bit+=ac.getState(rule,bit_ini[i:i+3])
        new_bit+='0'
        o.write(new_bit+"\n")
        bit_ini=new_bit
        new_bit='0'
    o.close()

Y la función que hice para determinar las reglas, aún no mejorada es esta:

def getState(rule,bits):
    '''Descripcion:
        Devuelve el estado de la celula a partir del estado
        de la cadena representada en bits siguiendo la regla
        representada por rule
        rule : entero entre 0 y 255
        bits: cadena de 3 caracteres de ceros y unos
    '''
    # Convierte el entero rule a binario de 8 bits representado por una cadena
    bin_rule=bin(rule)[2:].zfill(8)
    # Aplica la regla de Wolfram
    if bits=='000':
        b=bin_rule[7]
    elif bits=='001':
        b=bin_rule[6]
    elif bits=='010':
        b=bin_rule[5]
    elif bits=='011':
        b=bin_rule[4]
    elif bits=='100':
        b=bin_rule[3]
    elif bits=='101':
        b=bin_rule[2]
    elif bits=='110':
        b=bin_rule[1]
    elif bits=='111':
        b=bin_rule[0]
    return b

Esta es la primer entrega del capítulo 2 del libro. Algún otro domingo iré continuando con desarrollos que agregan más complejidad. Por lo pronto les dejo el famoso juego de la vida de conway

Las habladurías del mundo

Las huellas de quienes nos informan quedan  -por suerte- en la web. En una especie de repositorio de la historia reciente o futura. Hechos que recuerdo intensos pueden ser gratamente -o no- rememorados naufragando un poco.

Venía de comer con unos amigos donde últimamente -y por suerte- las discusiones políticas acaparan la escena, me pregunté qué carajo nos decían allá por el 2001, mientras era un estudiante universitario-puber-adolescente a la espera del famoso estirón que me debía la vida, aquellos medios gráficos ingenuamente incuestionados. Me llevé una sopresa al releer velozmente las tapas del GRAN DIARIO ARGENTINO, pero me cansé de ir bajando una a una cada portada.

Por ahí se dice que la característica que distingue a los informáticos es la pereza. Coincidiendo completamente con esta afirmación, me puse a programar con python para descargar automáticamente todas las tapas del diario clarin entre un intervalo de fechas dado. Toqueteando un poco otro script me armé esto:

def get_big_liar(file_name,file_mode,base_url,fecha):
	from urllib2 import Request, urlopen, URLError, HTTPError

	# Armo la url de "El Gran Diario Argentino (GDA)"
	fechaweb=fecha.strftime("%Y/%m/%d")+"/"
	url = base_url + fechaweb + file_name

	# Hago el request
	req = Request(url)

	# Abro url
	try:
		f = urlopen(req)
		print "downloading " + url
		# Armo el nombre de archivo usando la fecha
		local_file = open(fecha.strftime("%Y-%m-%d")+".jpg", "w" + file_mode)
		# Escribo el archivo localmente
		local_file.write(f.read())
		local_file.close()

	# handle errors
	except HTTPError, e:
		print "HTTP Error:",e.code , url
	except URLError, e:
		print "URL Error:",e.reason , url

# Para ir armando las fechas
import datetime

# Fecha inicio y final (anio, mes, dia)
fini=datetime.date(2001, 01, 01)
fend=datetime.date(2001, 12, 31)

# Una tapa por dia
one_day = datetime.timedelta(days=1)
# Nombre del archivo
file_name="portada.jpg"
# URL fija
base_url="http://edant.clarin.com/diario/"

# Itero entre el intervalo
while fini<=fend:
	get_big_liar(file_name,"b",base_url,fini)
	fini+=one_day

Corriéndolo vas a bajarte todas las tapas entre el 1 de enero y el 31 de diciembre de 2001. Fijate esta tapa del 4 de diciembre, es una joyita (me costó entender que no era la revista barcelona) :

Decían los chinos: Ojalá te toquen vivir tiempos interesantes.
Acá todas las tapas.

Mínimos*Mínimos = Mínimos cuadrados

Resulta útil describir la relación entre variables de un problema por medio de una expresión matemática.
Eso decía Stanley Grossman y estaba en lo cierto.

Cuando uno tiene una nube de puntos y quisiera analizar el comportamiento de esa distribución de valores es útil encontrar una ecuación que se aleje lo menos posible de cada uno de los puntos. Hacer esta aproximación es el archiconocido problema de mínimos cuadrados. Dependiendo el grado de la ecuación que se use será lineal, cuadrática, cúbica, etc.

Hecha esta simplificada introducción dejo un programa en python que a partir de pares de datos generados al azar hace una aproximación lineal. Para esto usé numpy y matplotlib.

from numpy import *
import matplotlib.pyplot as plt
#cantidad de puntos
n=20
random.seed(n)
x=linspace(0.0,1.0,n)
# un poco de ruido
ruido=random.normal(0,0.25,n)
# pendiente y offset
me=-2.0
be=3.0
# puntos: (x,ye)
ye=me*x+be + ruido
# grafico los puntos
plt.plot(x,ye,'o')
# Armo la matriz de Vandermonde
A=array([x,zeros(n)+1])
A=A.transpose();
# numpy hace el laburo pesado
result=linalg.lstsq(A,ye)
#pendiente y desplazamiento
#de recta de aproximacion
m,b=result[0]
plt.hold(True)
# le chanto arriba la recta aproximada
plt.plot(x,m*x+b)
plt.show()

Y nos genera una linda figurita de este tipo:

Nada más por el momento.

CCCP

El significado del título sale por siempre inspección: Computación Científica Con Python.

Existen una serie de módulos que hacen verdaderamente atractivo a Python como un lenguaje serio para tareas relacionadas con la computación científica. A lo largo de mi carrera (de grado y pos) he programado mas en Matlab que en lenguajes de propósito general. El argumento es válido, se necesita transmitir algún concepto al alumno y la forma más rápida sin perderse en prolegómenos del lenguaje es recurrir a estos entornos que permiten, leer datos, calcular, limpiar, procesar y finalmente visualizar con pocas sentencias y con un lenguaje amigable.

Aquí es donde entra en juego Python. Lo empecé a usar mas seriamente hace unos meses, justamente para realizar tareas de visualización, y me he sorprendido gratamente del desempeño y la escalabilidad del mismo. Por supuesto que siempre tenemos en cuenta que es un lenguaje interpretado, por lo que no pretendemos utilizarlo para realizar tareas de cálculo intensivo, al menos no de la forma clásica, ni esperando que tenga un rendimiento equivalente a C++.

El módulo fundamental para computación científica se denomina Numerical Python (en forma breve numpy) y contiene, entre otras cosas, las siguientes características (extraido de http://numpy.scipy.org/):

  • a powerful N-dimensional array object
  • tools for integrating C/C++ and Fortran code
  • useful linear algebra, Fourier transform, and random number capabilities
Como verán, añade a Python una estructura de datos fundamental: arreglos n-dimensionales. Esta estructura de datos además es soportada por decenas de otros módulos, por mencionar los dos más utilizados para visualización:  matplotlib (para 2D) y mayavi2 (para 3D).

Mayavi2 es una herramienta de propósito general independiente de la plataforma para visualización científica tri-dimensional. Algunas de sus características incluyen:

  • Visualización de datos escalares, vecotiales y tensoriales en 2 y 3 dimensiones.
  • Fácilmente programable desde Python.
  • Puede trabajar en forma transparente con arreglos numpy.
  • Fácilmente extensible.
  • Guardar las visualizaciones en varios formatos de imagen.
  • Funcionalidades convenientes para el ploteo científico a través del submódulo mlab.

La siguiente animación la hice con Numpy + Mayavi2 a partir de unos datos obtenidos de una simulación:

Por otro lado, me bajé de la nasa unas imágenes satelitales de Mendoza, y con ayuda de otros módulos (en otro post explicaré) + numpy + mayavi2 se puede explorar en forma interactiva (además de procesar para laburar obvio!), acá les dejo una captura :

Luego de un par de meses de internarme con Python y estos módulos que mencioné, logré resultados que serían muchísimo más complejos de obtener con un lenguaje como C++ o Fortran. Así y todo, aún se poco y nada sobre Python, pero ya con esto se pueden hacer grandes cosas y todo, como siempre, con Software Libre.

Guitar (la tocarra)

La cabeza suele nublarse con el laburo y las problemáticas cotidianas, esas tormentas casi siempre se me convierten en dolores de cabeza y a veces en migrañas. Nada mejor para despejar esos nubarrones que algo de deporte y actividades (pseudo)artísticas (en mi caso).

Entonces uno, muchas veces va a jugar al bolo (mal, pero va igual!). El tema es que el fulbito tiene una gran desventaja: no se puede usar la computadora en ningún momento.

Así es que decidí retrotraerme a mis momentos adolescentes y comprarme una viola para darle un poco de swing a mi vida. Fui, la compré, y empecé a tocar hasta que los dedos me quedaron mochos. Ahora bien, luego de tanto tiempo sin tocar (casi 15 años y la RPMadreQMP!!!) algunas notas ya no me las acordaba, o me vas a decir que Gsus4 es auto-explicativa?? Noo, ni ahí!!

Aquí es donde entra en juego la compu, que sin GNU/Linux no se si se la podría llamar compu. La cuestión es que encontré TuxGuitar . Un software multipista, que permite -entre otras cosas- afinar la viola, armar las tablaturas (o si sabés las partituras también), insertar las ya conocidas y finalmente reproducirlas. Ojo, yo no le saqué el brillo, pero lo utilizo para que me muestre cuales son las notas que mi memoria ya no puede sacar a la luz.

Aquí les dejo una captura, lo recomiendo ampliamente!

PD: lo del futbol es en chiiiiste, soy re bueno!

Social Widgets powered by AB-WebLog.com.

Social Widgets powered by AB-WebLog.com.

Social Widgets powered by AB-WebLog.com.