INTRODUCCION AL USO DE CLASES EN PYTHON.

Python es un lenguaje de programación versátil y potente que se destaca por su facilidad de uso y legibilidad. Una de las características clave de Python es su capacidad para trabajar con clases, que permiten crear objetos y estructurar el código de manera eficiente. En este artículo, exploraremos el uso de clases en Python (junto a algunos conceptos clave) y cómo pueden mejorar tu código, junto con algunos ejemplos prácticos. Pero antes, empezaremos por lo más básico: Definir que es una «clase» en Python:

1). ¿QUÉ ES UNA CLASE?

En Python, una clase es una plantilla o un plano para crear objetos. Una clase define las propiedades y los comportamientos que tendrán los objetos que se creen a partir de ella. Las propiedades se llaman atributos y los comportamientos se llaman métodos. Los atributos son variables asociadas a la clase y los métodos son funciones asociadas a la clase.

2). DECLARACIÓN DE UNA CLASE.

Para declarar una clase en Python, se utiliza la palabra reservada «class» seguida del nombre de dicha clase. A continuación, te mostramos un ejemplo básico de declaración de una clase en Python:

En este ejemplo, hemos creado una clase llamada «Persona» con dos atributos («nombre» y «edad«) y un método llamado «saludar» que imprime un saludo personalizado. Luego creamos dos objetos de la clase Persona, «persona1» y «persona2«, y llamamos al método «saludar» en cada objeto.

OUTPUT:

3). HERENCIA DE CLASES.

La herencia de clases es un concepto importante en la programación orientada a objetos, el cual, permite crear una clase nueva basada en una clase ya existente, heredando sus atributos y métodos. A esta nueva clase la llamamos clase derivada o subclase, mientras que la clase existente recibirá el nombre de clase base o superclase:

Como se ve en este ejemplo, creamos una nueva clase «Estudiante» que hereda de la clase «Persona«. Por su parte, la clase «Estudiante» tiene un atributo adicional «curso» y un método adicional «presentarse«. Utilizaremos la función «super()» para llamar al método «init» de la clase base y aprovechar los atributos heredados de esta.

OUTPUT:

4). ENCAPSULACIÓN.

La encapsulación es un principio de la programación orientada a objetos que permite ocultar los detalles internos de una clase y proporcionar una interfaz para interactuar con los objetos. En Python no existe como tal (al no haber diferencia entre atributos/métodos públicos y privados), pero se puede simular precediendo dichos atributos y métodos con dos barras bajas («__«) como indicando que son especiales, evitando, así, que se pueda producir un acceso no deseado, a los mismos:

En este ejemplo, la clase «CuentaBancaria» tiene un atributo privado «__saldo» al que solo se puede acceder a través de un método público llamado «obtener_saldo«. Esto protege el saldo de la cuenta y evita su modificación directa.

OUTPUT:

CONCLUSIÓN.

Las clases en Python son una herramienta poderosa para estructurar y organizar el código de manera más eficiente. Permiten encapsular datos y comportamientos relacionados en objetos, facilitando su reutilización y mantenimiento. Además, la herencia de clases ofrece la capacidad de extender y especializar las clases existentes. Al dominar el uso de clases en Python, puedes escribir programas más limpios, modulares y fáciles de entender.

Recuerda que estos ejemplos solo representan una introducción al uso de clases en Python, y hay muchas más posibilidades y conceptos avanzados (que iremos viendo en futuros artículos) los cuales, puedes explorar para aprovechar al máximo la programación orientada a objetos en este lenguaje tan versátil. ¡Anímate a seguir aprendiendo y experimentando!

Podéis acceder a los códigos utilizados este artículo, en los siguientes enlaces:

https://github.com/antonioam82/ejercicios-python/blob/master/ejem_clases.py

https://github.com/antonioam82/ejercicios-python/blob/master/ejem_clases2.py

Saludos.

USANDO «CHATGPT» DESDE PYTHON.

ChatGPT es la herramienta de IA más popular con la que podemos chatear, obteniendo respuestas que sorprenden por su grado de coherencia y precisión. Una herramienta online a cuyas funcionalidades principales podemos acceder directamente a través de Python y una librería creada con ese propósito: «openai» y de cuyo manejo más básico hablaremos hoy, empezando por su instalación en nuestro sistema, que realizaremos, como venimos haciendo, con el comando «pip«:

Hecho esto, ya tendremos nuestra librería lista para ser usada en Python. Sin embargo, debemos tener en cuenta que para acceder a las respuestas de «ChatGPT» necesitamos una «API Key«, consistente en una clave que generaremos abriéndonos una cuenta en la API, para la que deberemos usar nuestro correo y número de teléfono para verificar:

Una vez creada la cuanta nos dirigiremos a la sección «View API Key» para nuestra clave de aplicación, que deberemos usar en nuestro script de Python.

Hecho ello, ya podemos empezar a usar Python para acceder a ChatGPT. Para ello, empezaremos creando un archivo (al que llamaremos «chat.py«) en el que empezaremos importando la librería instalada «openai» y definiendo la variable «key» que será igual a la clave que hayáis generado para la API:

Hecha la importación y establecida la clave, podremos realizar nuestra primera consulta desde Python, en pocas líneas de código:

Como se ve, lo primero que hacemos es definir la variable «prompt» a través de la cual, introduciremos la pregunta o mensaje que queramos enviar a ChatGPT. Por su parte, la variable «completion» contendrá la respuesta que recibamos de la aplicación, para la que tendremos que especificar las variables «engine» (el nombre del modelo entrenado que queramos usar, pudiéndose consultar estos modelos en la página de la API), «prompt» (el mensaje que queremos enviar) y «max_tokens» (mediante el que especificaremos la extensión máxima de la respuesta que queramos recibir. Para mostrar el mensaje usaremos «choices[0]» para obtener el primer mensaje generado. Con ello podremos pasar a ejecutar nuestro programa para realizar nuestra primera consulta:

OUTPUT:

Tal y como lo hemos escrito, nuestro programa finalizará una vez obtenida la respuesta. No obstante, podemos usar un bucle que nos permita hacer preguntas a la aplicación de modo indefinido hasta introducir un determinado caracter o string («END» en nuestro ejemplo):

OUTPUT:

Y de este sencillo modo podremos realizar consultas a «ChatGPT» directamente desde nuestra terminal utilizando nuestro lenguaje Python. Para más información acerca de las opciones que ofrece y de su uso, tenéis más información en la página del proyecto:

https://pypi.org/project/openai/

https://github.com/antonioam82/ChatPy

Saludos.

FINANZAS CON PYTHON: CALCULO DEL VALOR EN RIESGO DE UNA INVERSIÓN.

El «valor en riesgo» («VaR» en adelante) consiste (como su nombre indica) en una medida del riesgo de una determinada acción, consistente en determinar la pérdida que se podría sufrir en condiciones normales de mercado en un intervalo de tiempo y con un cierto nivel de probabilidad o de confianza. Viendo en que consiste, es lógico pensar que se trata de una medida muy utilizada en economía y que, en esta ocasión, nos disponemos a calcular utilizando «Python».

Visto someramente en que cosiste el «VaR«, pasaremos a realizar un sencillo ejemplo en Python, ayudándonos de las librerías «yfinance«, «numpy» y «matplotlib«, en el que pasaremos a medir el riesgo de invertir en una determinada compañía como puede ser «Tesla«:

Como se ve en la imagen, hemos empezado importando todos las librerías y módulos que vamos a necesitar para el ejercicio. A continuación, hemos usado la función «Ticker()» de «yfinance» para definir la empresa cuya serie de resultados queremos obtener pasándole como argumento su correspondiente «ticker» o símbolo, para acto seguido, emplear la función «history()» (especificando la fecha de inicio de la serie y el intervalo de tiempo en el que queremos que se muestren los datos). Almacenando toda esa información en la variable «df» de la que solo tomaremos los valores de cierre y cuyos primeros valores hemos mostrado al final.

También podemos utilizar «matplotlib» y su función «plot()» para graficar los datos de cierre (que para nuestro ejercicio, son los que nos interesan) no sin antes asignar estos últimos a la variable que hemos llamado «tesla_cierre«:

OUTPUT:

Con todo ello, ya tenemos nuestra serie temporal de datos. Sin embargo, dado que para el cálculo del «VaR» necesitamos contar con una distribución de probabilidad, los datos tal y como los tenemos ahora no nos valdrían, siendo necesario aplicarle algunas transformaciones. Concretamente, necesitaremos convertir la serie de no estacionaria (lo cual ya se aprecia facilmente en la gráfica, al verse una tendencia clara en la misma) en estacionaria (con media y varianza constantes). Algunos de los procedimientos para la realización de dicha transformación son el uso de logaritmos y la diferenciación de la serie, consistente en calcular para cada valor, la diferencia entre dicho valor y su correspondiente valor anterior lageado «n» veces. En nuestro caso vamos a hacer uso conjunto de ambas técnicas usando un retardo (o «lag») de 1 (lo que significa que para el cálculo de las diferencias, restaremos a cada valor su correspondiente valor anterior.

Aquí hemos guardado en una nueva variable «tesla_retornos» las diferencias de los logaritmos (para lo que usamos la función «log()» de «numpy«) con un retardo de un solo valor (lo que hemos definido como argumento de la función «shift()«. Finalmente podemos aplicar la función «dropna()» para asegurarnos de que la serie no contenga valores vacíos.

Hecho todo ello, podemos visualizar la gráfica de los retornos con «matplotlib» de modo que podamos comprobar como (salvo alguna desviación puntual) los valores ahora se distribuyen entorno a una media, de forma constante:

OUTPUT:

Retornos logarítmicos.

Una vez que tengamos nuestra serie de datos estacionales, estamos, por fin, en condiciones de hacer el cálculo del «VAR«. Para ello, necesitábamos definir un espacio de tiempo (lo que ya hemos hecho, siendo este de un año), un intervalo de confianza (en nuestro caso vamos a realizar el cálculo para un 95% de confianza) y una inversión inicial, que en nuestro caso definiremos en la variable «inv_inicial«:

Tal y como puede verse, hemos realizado el cálculo del «VaR» para un intervalo de confianza del 95% (con lo que el percentil que aplicaremos será 5 (100-95). Dicha variable la introduciremos como argumento, junto a la serie diferenciada, en la función «percentile()» lo que nos devolverá un porcentaje de la cantidad invertida. Para obtener la cantidad perdida simplemente multiplicaremos el resultado por el valor de «inv_inicial«:

Tal y como se comenta aquí, el resultado obtenido nos estará indicando la existencia de un 95% (el intervalo de confianza) de probabilidades de que, con una inversión inicial de 1500€, obtengamos una pérdida diaria inferior al 0.074% de dicha inversión (unos 111.027€) o lo que es lo mismo, un 5% de probabilidades de que dicha perdida sea igual o superior a esa cifra, en un día, para el plazo establecido.

A partir de este punto también puede ser de interés el calculo del valor en riesgo condicional (consistente en la media de los valores que se encuentran por debajo del «VaR«):

Saludos.

USANDO ARBOLES DE DECISIÓN EN PYTHON.

Un «árbol de decisión» consiste en un método de clasificación, ampliamente utilizado en el ámbito del «aprendizaje automático» que nos permite la predicción y clasificación de una variable categórica a través de la construcción de un diagrama en arbol (de donde viene su nombre). Así, en el artículo de hoy vamos a construir nuestro propio arbol de decisión, usando varias librerías («numpy«, «pandas«, «matplotlib» y «sklearn«) siendo esta última la que contiene los métodos y funciones tanto para generar el mismo como para realizar el proceso de clasificación y comprobación de su precisión. Y que como el resto de librerías, deberemos instalar previamente en nuestro equipo (aunque en este caso utilizaremos la plataforma «Google Colab» para la ejecución de nuestros scripts):

Así, lo que nos proponemos a hacer en este ejercicio es, a partir de los datos médicos de una serie de pacientes y de su edad, almacenados en un «csv», determinar que pacientes van a desarrollar una enfermedad. Por ello, lo primero que haremos será cargar la información para ver que contiene. Para la lectura de nuestro archivo «csv» (que lleva por nombre «Pacientes2.csv«) usaremos la función «read_csv()» de la librería «pandas«:

Como puede verse en la imagen, obtenemos un dataset con la información de una serie de pacientes, identificados por un número, de los que se indican la presencia o no (representadas por ‘0’ y ‘1’ respectivamente) de determinadas características (hipertensión, hiperglucemia, si es fumador…), el sexo (codificado nuevamente con ‘0’ y ‘1’) y edad. Finalmente en la columna «Enfermedad» se registra si dicho paciente a registrado o no alguna enfermedad (siendo esta variable la que nos disponemos a predecir).

De este modo lo nos proponemos a hacer es construir un «arbol de decisión» que nos sirva para clasificar (o predecir) la posibilidad o no de desarrollar una enfermedad a partir de unos datos de entrenamiento. Hecho esto, pasaremos a evaluar la precisión del mismo.

A continuación, utilizaremos la función «.info()» para obtener algunos datos generales acerca de nuestro dataset como pueden ser el tipo de dato para cada columna, el número de estas y el número de filas:

Vemos así, que nuestra tabla consta de un total de 11 columnas y 985 filas. Esta información es importante de cara a establecer cuales van a ser nuestras variables predictoras, las filas que vamos a utilizar para entrenar el modelo y las filas que usaremos para testearlo. Empezaremos definiendo las variables predictoras y la variable a predecir:

Para ello, creamos dos objetos (‘X‘ e ‘Y‘) en los que almacenamos las variables predictoras (las cuales definimos con la función «.iloc()» pasándole el rango correspondiente a estas) y la variable a predecir (columna 0). Finalmente usamos «.head()» para mostrar las primeras filas de las variables predictoras (lo mismo podemos hacer para la variable a predecir).

También haremos la división entre los datos de entrenamiento y los datos de testeo. Para lo cual, utilizaremos el módulo «train_test_split» de la librería «sklearn«. Estableciendo a su vez, que emplearemos el 80% de los datos para entrenar el modelo (usando el 20% restante para probarlo):

Usando la función «.info()» aplicada a la variable «X_train» (en la que hemos almacenado los datos de entrenamiento) podemos ver como esta se compone de 788 registros. A continuación, pasaremos a usar estos registros para entrenar el modelo, usando la función «fit()» a la que pasaremos las variables predictoras («X_train«) y la variable a predecir («Y_train«) de nuestros datos de entrenamiento:

Esto nos generará el correspondiente arbol de decisión, el cual, podremos representar gráficamente con la ayuda de la librería «matplotlib» y en el que se muestra el proceso de clasificación de los datos seguido para la creación del modelo predictivo:

OUTPUT:

Por su parte podemos guardar nuestra gráfica como un archivo de imagen, mediante la función «savefig()«:

Viendo la figura generada, se ve como esta se compone de una serie de nodos que a su vez se ramifican en otros. Cada uno de dichos nodos viene representado por una caja en la que se muestra información sobre el mismo:

En cada una de las cajas veremos reflejada en primer lugar, la condición concreta que se ha aplicado en la clasificación del nodo (en el caso de la imagen, si el valor de la variable «hiperglucemia» es menor o igual a 0.5), el índice «gini«, que mide el grado de pureza del nodo (como de ordenados están los datos), el número de pacientes incluidos en el nodo, el número de valores «NO» y «SI«, y la categoría predominante («NO» en este caso).

A su vez, podemos ver las predicciones realizada acerca de la variable dependiente (que recordemos era la correspondiente a la columna «Enfermedad«) para el conjunto de datos de prueba:

Una vez generado el modelo y realizada las predicciones sobre los datos de prueba, pasaremos a comprobar la efectividad y grado de acierto de nuestro modelo, mediante la comparación entre los valores predichos para la variable «Enfermedad» y los datos reales para esta misma. Para esto último usaremos la función «confusion_matrix()» de «sklearn.metrics«:

Obtenemos una matriz en cuyas filas superior e inferior se muestran el numero de filas cuya etiqueta real es ‘NO‘ y ‘SI‘ respectivamente (es decir: que tenemos 150 individuos cuyo valor real es ‘NO‘ y 47 cuyo valor real es ‘SI‘). A su vez en cada columna se muestra los valores predichos como ‘NO‘ y ‘SI‘. Con lo que se deduce que los valores predichos acertadamente por el modelo son los correspondientes a la diagonal principal, los cuales suman 190, mientras que la otra diagonal se correspondería con las predicciones incorrectas (7 en total).

Finalmente, haciendo uso de «numpy» podemos hacer el cálculo, tanto de la precisión global del modelo, así como de la precisión para cada categoría:

Obteniendo así, el valor de precisión (entre 0 y 1) tanto a nivel global, así como para cada una de las clases «SI» y «NO«.

Saludos.

ACCEDIENDO A DATOS METEOROLOGICOS EN PYTHON, CON «meteostat».

Saludos y bienvenidos una semana más a este blog sobre programación en lenguaje Python. En el día de hoy, vamos a hablar de «meteostat» una interesante librería mediante la cual, podremos acceder a los datos meteorológicos recogidos por distintas estaciones alrededor del mundo.

Pero lo primero es lo primero, y antes de empezar a practicar con ella, deberemos proceder a su instalación en nuestro equipo, utilizando el procedimiento que acostumbramos:

Una vez que tenemos instalada la librería en nuestro sistema, podemos comenzar a obtener datos climáticos basados en la información recogida por distintas estaciones meteorológicas en función del área que estemos estudiando. Por ejemplo, digamos que queremos obtener la evolución por días (en una gráfica) de las temperaturas máxima, mínima y media, en el área de París durante el año 2022. Para ello empezaremos importando las librerías de las que nos vamos a valer para ello:

Se ve como, junto a los métodos «Point» (para establecer las coordenadas deseadas) y «Daily» (pues queremos obtener datos diarios) de la librería «meteostat«, realizamos también la importación de «matplotlib» (para graficar los datos), «datetime» (para fijar el periodo de tiempo a estudiar) y «geopy» para obtener las coordenadas del área de estudio. Tras ello, empezaremos utilizando esta última para obtener la latitud y longitud en la que se ubica la ciudad en cuestión:

Como se ve, empezamos creando un objeto («loc«) mediante el cual, vamos a proceder a geolocalizar la ciudad de nuestro interés. Cuya latitud y longitud obtendremos mediante los métodos «latitude» y «longitude» respectivamente. Valores estos que almacenaremos en las variables «lat» y «long«. La segunda información que vamos a determinar es el periodo de tiempo de nuestra serie histórica diaria. Como dijimos, en este caso vamos a mostrar los datos para el año 2022, usando «datetime» para fijar el inicio y el final de la serie temporal, almacenando tales datos en las variables «start» y «end» respectivamente:

Con esta información ya estamos en disposición de obtener nuestros datos meteorológicos para la villa de París. Esto lo haremos utilizando primero el método «Point()» (al que pasaremos la latitud y la longitud antes obtenidas) para fijar el punto concreto cuyos datos climáticos queremos obtener y en segundo lugar, el método «Daily()» (pasándole el punto obtenido, el inicio de la serie temporal y su final) para obtener los datos climáticos diarios para dicho punto en ese intervalo de tiempo:

Obtendremos así, una tabla resumida (con las 5 primeras y 5 últimas filas de la serie) con datos climáticos tales como temperaturas, lluvias, nieve, presión atmosférica, vientos. Para nuestra representación gráfica, vamos a quedarnos solamente con la información referente a las temperaturas media, mínima y máxima (las tres primeras columnas) que pasaremos en una lista como argumento de la función «plot()» de «matplotlib«:

OUTPUT:

Evolución diaria de la temperatura media, mínima y máxima para el área de París durante el año 2022.

Obtendremos de este modo, una visualización de las temperaturas diarias para el periodo especificado.

Con esto hemos visto la manera en que podemos extraer los datos históricos del clima de una región, para un tiempo determinado. Sin embargo, en ocasiones, resulta útil obtener información acerca de las estaciones que hemos utilizado para obtener los datos. Es por ello que «meteostat» incluye un módulo llamado «Stations» mediante el cual, podremos obtener dicha información:

Se nos muestra un tabla con las 12 estaciones cercanas del área de interés (12 por que es el número que hemos introducido como argumento en la función «fetch()«). Hemos de notar que en este caso y por motivos de espacio, la tabla solo muestra 3 de las 16 columnas que la componen (el identificador ID, el nombre de la estación y la distancia). En el siguiente cuadro se muestran el nombre de las 16 columnas que componen las tablas:

No obstante, siempre podemos acceder a la información de cualquiera de las columnas utilizando el procedimiento que conocemos para acceder a las columnas de cualquier dataframe:

Y hasta aquí esta breve presentación de «meteostat» una librería que sin duda nos será de gran utilidad a la hora de recopilar información meteorológica de cualquier parte del mundo, para la realización de cualquier proyecto, estudio o incluso elaboración de modelos predictivos para clima, en Python.

Saludos.

CREAR GIFS ANIMADOS DESDE LA LINEA DE COMANDOS.

Hola programadores. Como ya sabrán, en esta página nos gusta de vez en cuanto, realizar sencillos proyectos haciendo uso de conceptos, librerías y recursos de los que ya hemos hablado en artículos anteriores, y el de esta semana es uno de ellos, porque nos proponemos a realizar un script (cuyo código completo podéis consultar a través del link que dejamos al final del artículo) que nos permitirá generar gifs animados a partir de archivos de video, directamente desde nuestro CMD mediante la introducción de una serie de argumentos:

  • -src/–source: Nombre del vídeo original (obligatorio).
  • -dest/–destination: Nombre del archivo a generar (opcional).
  • -sz/–size: Tamaño en porcentaje del gif respecto al vídeo original (opcional).
  • -shw/–show: Muestra resultado en ventana emergente al finalizar el proceso de generado (opcional).
  • -st/–start: Segundo inicial para gif (opcional).
  • -e/–end: Segundo final (opcional).
  • -spd/–speed: Velocidad relativa de la animación (opcional)

Así, crearemos un archivo «mkgif3.py» en el que empezaremos haciendo la importación de las librerías y recursos que vamos a necesitar, entre las que destaca «argparse» que, como vimos en su momento, nos permitirá la introducción de argumentos a través de la terminal:

Realizadas las importaciones necesarias, definiremos una función «main()» que será la primera en ejecutarse, y que se encargará de leer los valores introducidos por la terminal, para nuestro programa creando primero el objeto «parser» para luego ir añadiéndole argumentos mediante la función «add_argument()» en la que especificaremos datos tales como el tipo de dato, valor por defecto, nombre de argumento así como la información de ayuda:

Así, estableceremos nuestros argumentos de modo que al introducir en el terminal, el nombre de nuestro archivo «.py» seguido de «-h» se nos muestre la información relativa al mismo (nombre y descripción) así como los argumentos, variables y sus características:

Tal y como se muestra en la descripción, nuestro programa nos permitirá generar gifs de archivos de vídeo así como convertir archivos «.webp» en «.gif». También podemos incluir la dirección web de nuestro proyecto.

Una vez leídos los argumentos y almacenada su información en la variable «args«, haremos la llamada a la función encargada de generar nuestro gif (función «gm()«) que tomará como argumento la información recopilada en dicha variable:

Tal y como hemos señalado, la función «gm()» se encargará de la generación de nuestro «gif» a partir de los datos introducidos en la terminal. Como se ve, con respecto a la información introducida, primero se comprobará si el archivo fuente es de una extensión válida (las cuales habremos definido en una lista a la que hemos llamado «suported_formats«) o «.webp» y si el archivo de destino es de extensión «.gif«. De modo que de no cumplirse tal condición se nos mostrará un mensaje de error:

La segunda condición que se evaluará es si el archivo de video introducido como fuente («args.source«) se encuentra en el directorio de trabajo, mostrándose el correspondiente mensaje de error, en caso contrario:

Comprobadas estas condiciones, nuestra función generará nuestro gif a partir de la información suministrada (fuente, duración, velocidad, tamaño…). Para la aplicación de estas características usaremos la librería «moviepy«. Para establecer el inicio y final de nuestro gif usaremos los argumentos «args.start» y «args.end» que se corresponderán por defecto con el segundo inicial y final del vídeo, respectivamente:

Como se ve, hemos incluido dos funciones a ejecutar una vez completada la tarea. Una de ellas es la función «show()» que solo se ejecutará si introducimos la opción «-shw/–show» y que mostrará en una ventana emergente, el archivo gif creado, el cual tomará como único argumento:

La otra función es «get_size_format()» que devolverá el tamaño del archivo generado con su correspondiente unidad, en función del mismo:

Finalmente, hemos añadido unas líneas al inicio de nuestro código mediante las cuales y usando las librerías «colorama» y «pyfiglet» (de las que también hemos hablado) daremos una presentación a nuestro script, con el nombre del mismo (que se mostrará el ejecutarse la función «gm()«), de un color que será distinto cada vez que ejecutemos la función principal. También definiremos la variable «supported_formats» a la que nos referimos antes:

Y hasta aquí esta sucinta exposición de nuestro script para generar gifs animadas a partir de archivos de vídeo, desde la línea de comandos y cuyo código completo podéis encontrar en el siguiente enlace:

https://github.com/antonioam82/MKGIF/blob/main/mkgif3.py

Versión actualizada:

https://github.com/antonioam82/MKGIF/blob/main/mkgif4.py

Saludos.

MÉTODO, PASO A PASO, PARA DIVISIÓN ENTRE MATRICES, CON PYTHON Y «numpy».

Como muchos de ustedes ya sabrán, «numpy» es una librería de gran utilidad a la hora de crear y operar con matrices y vectores, utilizando una amplia gama de funciones matemáticas de alto nivel, con la que ya hemos trabajado en más de una ocasión. Pues bien, en el presente artículo vamos a utilizarla de nuevo para ejemplificar como podemos usarla para realizar divisiones entre matrices. Operación que si bien no puede efectuarse como tal entre matrices, si existe un procedimiento para ello, que solo se podrá efectuar bajo unas condiciones. Veámoslo con un sencillo ejemplo que iremos codificando en Python, usando «numpy«. Librería que deberemos tener instalada y que de no ser así deberemos hacerlo previamente para continuar:

Supongamos que tenemos dos matrices «X» y «B» de 3×3 (3 filas y 3 columnas) cada una:

Procederemos a crear ambas matrices. Para ello, podemos utilizar las funciones «array()» o «matrix()«. En este caso usaremos la segunda de ellas del modo siguiente:

Tal y como hemos señalado con anterioridad vamos a efectuar nuestra división, poniendo la matriz «X» en el numerador y la matriz «B» en el denominador, lo cual, expresado algebraicamente, nos lleva a las siguientes igualdades:

Lo que nos lleva a que para realizar nuestra división, tendremos que multiplicar nuestra matriz «X» por la inversa de «B» (para lo cual el número de columnas de la primera a de ser el mismo que el número de filas de la segunda). Una operación sencilla que haremos teniendo en cuenta que para ello, la matriz «B» debe ser invertible. Lo que implica el cumplimiento de dos características que deberemos comprobar previamente:

  • Que se trate de una matriz cuadrada (mismo número de filas y columnas).
  • Que el valor de su determinante sea distinto de 0.

Respecto al primer requisito (mismo número de filas que de columnas) es una característica de fácil comprobación que en todo caso, podremos obtener en «numpy» mediante la función «shape()» que recibiendo como argumento, la matriz en cuestión, nos devolverá una tupla de valores con el número de filas y de columnas:

Tal y como hemos dicho, la segunda característica que debemos comprobar es si el valor de la determinante de la matriz es distinto de 0. Calcularemos la determinante de la matriz cuadrada, mediante la diferencia entre el producto de los elementos de la diagonal principal y el producto de los elementos de la otra diagonal tal y como se muestra a continuación:

Procedimiento para calcular la determinante de una matriz.

Para efectuar dicho cálculo con «numpy» usaremos la función «det()» pasando como argumento la variable que contiene la matriz cuyo determinante queremos obtener:

De este modo, quedan comprobados las dos características necesarias para que nuestra matriz «B» (que, recordemos, es la que tenemos como denominador en la operación) sea invertible. Ahora el siguiente paso será calcular la inversa. La inversa de una matriz es aquella que multiplicada por esta, da como resultado una matriz identidad (una matriz cuadrada cuyos elementos son 0 a excepción de los de su diagonal principal, que serán 1):

Matriz Identidad.

Se trata este de un cálculo más complejo, que con «numpy» podemos efectuar de un modo muy sencillo mediante el uso de la función»inv()«:

Obtenida la inversa, podemos comprobar lo antes dicho (que el producto de la inversa por su matriz nos devuelve una matriz identidad) mediante una multiplicación usando la función «dot()» que nos devolverá un resultado, cuyos valores convertiremos a enteros con la función «astype()«:

Una vez que tenemos la inversa de «B» (almacenada en la variable «invB«) solo nos quedará realizar la multiplicación de la matriz numerador «X» por dicha inversa. Esto lo haremos mediante la función «dot()«, poniendo atención al orden en el que introducimos los argumentos (primero numerador y luego denominador/inversa) ya que en la multiplicación de matrices no rige la propiedad conmutativa (aquí el orden de los factores si altera el producto):

Se obtiene así el resultado de la operación entre nuestras dos matrices.

Saludos.

ECUALIZACIÓN DE HISTOGRAMAS EN PYTHON, CON «opencv».

Hola y bienvenidos a un nuevo artículo de vuestro blog sobre programación en lenguaje Python, en el que utilizaremos «opencv» para llevar a cabo la ecualización del histograma de una imagen en escala de grises, consistente en la aplicación de un algoritmo que redistribuye los valores de intensidad de esta, logrando una distribución más uniforme. Lo que a su vez dará como resultado, un mayor contrate en la misma.

Pero antes de empezar, deberemos de asegurarnos de tener correctamente instaladas las librerías y recursos que vayamos a utilizar, procediendo a su instalación en caso contrario:

Para nuestro ejemplo, vamos a trabajar con el siguiente archivo de imagen, el cual deberemos cargar usando la función «imread()«. No sin antes hacer las importaciones pertinentes.

No obstante, la ecualización de histogramas es una técnica que solo nos va a servir sobre imágenes con un único canal de color. Por ello, nada más cargar la imagen, deberemos convertirla a escala de grises. Tras ello, usaremos «matplotlib» para mostrarla en pantalla:

OUTPUT:

Dada la naturaleza de la practica que nos ocupa, también será de interés mostrar un histograma en el que se muestre la distribución de los valores de intensidad de la imagen que mostraremos junto a la media de dichos valores (que calcularemos con la función «mean()» de «numpy«) y que representaremos en el histograma, con una línea vertical. Esto lo haremos definiendo una función («show_hist()«) que recibirá como argumentos, el titulo del histograma y el array que contiene los valores de intensidad para calcular el histograma:

De este modo, de nuestra imagen original en escala de grises (cuyos valores hemos almacenado en la variable «gray«) presentará la siguiente distribución:

Lo que nos proponemos a hacer a continuación es realizar una redistribución de los valores de intensidad de la imagen de modo que tengamos una mayor cantidad de pixeles, cuyos valores de intensidad se encuentren distribuidos de un modo más uniforme. Lo que a su vez, repercutirá en la presencia de un mayor contraste en la imagen. Para ello, tenemos una función en «opencv» llamada «equalizeHist()» la cual aplicaremos a nuestra imagen en gris:

OUTPUT:

Se obtiene así una imagen con un mayor contraste en las intensidades de gris. No obstante, también es cierto que si bien, esta función incrementa el contraste de la imagen, también aumenta el nivel de ruido que pueda tener esta además de aparecer como difuminada sobre todo en las regiones más claras. Por su parte, podemos usar nuevamente la función «show_hist()» para mostrar el nuevo histograma:

Es debido a los defectos antedichos por lo que puede interesar la aplicación de otro algoritmo, el «Contrast Limited Adaptive Histogram Equalization» (o «CLAHE«) que lo que hará será realizar la redistribución de valores de forma local, dividiendo la imagen en celdas sobre cuyos pixeles se hará el proceso de ecualización y cuyas dimensiones deberemos definir buscando un mejor resultado, definiendo también, un umbral límite para dicha transformación. Estas variables son las que introduciremos como argumentos de la función «createCLAHE()» la cual se encargará de la aplicación de dicha técnica:

OUTPUT:

Obtenemos nuevamente una imagen de mayor contraste sin perdida de información solo que sin la presencia de ruido y sin el efecto de lavado sobre la misma que apreciábamos en el caso anterior. A su vez, la más uniforme distribución de los valores de intensidad (incrementando el valor de las intensidades más bajas y disminuyendo el de las más altas), puede apreciarse viendo el histograma correspondiente a la nueva imagen:

Como se ve, la ecualización de histogramas es una técnica que nos puede ser de gran utilidad a la hora de dotar de un mayor contrate a imágenes en blanco y negro o escala de grises. Existe una función en «opencv» llamada «normalize()» mediante la cual, y usando la técnica de la normalización, podemos hacer algo muy parecido sobre imágenes a color. Pero de ello hablaremos en otra ocasión.

Podéis encontrar el código completo de este tutorial en el siguiente enlace:

https://github.com/antonioam82/ejercicios-python/blob/master/clahe.py

Saludos.

GENERAR DATAFRAME DESDE UN ARCHIVO DE TEXTO CON ‘PANDAS’.

Continuamos nuestra series de artículos relacionados con la librería «pandas» mostrando en esta ocasión, como podemos generar un dataframe a partir de los datos almacenados en texto plano en un archivo «txt«. A su vez, veremos como podemos almacenar dicha información en un archivo excel.

En este caso tenemos un archivo de texto, de nombre ‘symbols.txt‘, que contiene información acerca de las empresas que cotizan (o han cotizado) en el índice ‘Nasdaq‘ y con el que queremos trabajar accediendo a su información:

El problema aquí radica en el hecho de que la información se presenta en un formato cuya lectura resulta poco clara y con la que no podemos trabajar. Por ello vamos a usar «pandas» para, en primer lugar, crear un dataframe que nos permita un acceso sencillo a la información. Para ello, cargaremos nuestra información usando la función «read_csv()«:

Para ello, simplemente tendremos que introducir como primer argumento, la ruta al archivo que queremos acceder (o solo el nombre del mismo si se encuentra ubicado en el directorio de trabajo). Por su parte, dado que en el archivo de texto, en la primera fila, los nombres de las columnas están separados por comas, utilizaremos dicho carácter como criterio para separar dichas columnas («sep=»,»«). Para asegurarnos de que los datos se han cargado correctamente, podremos usar las funciones «.head()» y «.tail()» para mostrar las 5 primeras columnas o las 5 últimas, respectivamente:

A su vez, también podemos crear nuestro dataframe accediendo únicamente a determinados datos. En nuestro ejemplo, vamos a crear una nueva tabla que contenga solamente los símbolos de las compañías. Para ello, introduciremos entre corchetes , el nombre de la columna cuya información queramos incluir:

A su vez, podemos crear un nuevo dataframe que contenga solo algunas de las columnas del original. Así, supongamos que queremos una tabla en la que se muestre solamente el simbolo y nombre de la compañía respectiva. Para ello introduciremos la variable «columns» a la que pasaremos la lista de columnas que queremos usar:

Finalmente, podemos utilizar la función «to_excel()» para pasar los datos leídos desde nuestro archivo de texto a un archivo excel:

Y hasta aquí este artículo en el que hemos visto como cargar y acceder en Python, a la información almacenada en un archivo de texto, mediante la generación de un dataframe y el acceso a la información de sus columnas para después mostrar como podemos pasar dichos datos a un archivo excel.

En el siguiente enlace, podéis acceder a la información contenida en el archivo «symbols.txt» utilizado en este tutorial:

https://github.com/antonioam82/ejercicios-python/blob/master/symbols.txt

Saludos.

CALCULANDO Y GRAFICANDO CORRELACION ENTRE VARIABLES EN PYTHON.

Bienvenidos a vuestro sitio sobre programación en Python, en una ocasión en la que tal y como reza el título de este artículo, vamos a aprender un modo sencillo de calcular y graficar la correlación existente entre las variables de una tabla, de un modo sencillo, usando las librerías «pandas» y «matplotlib«.

Para empezar, diremos que la correlación entre dos variables es la medida estadística que expresa hasta qué punto dos variables están relacionadas linealmente. Es decir, nos dice en que medida la variación del valor se una variable «A» afecta en la misma medida al valor de otra variable «B» y viceversa. Se trata de una herramienta común para describir relaciones simples entre variables que en Python podemos calcular con la ayuda de la librería «pandas» y su método «.corr()«.

Para nuestro ejemplo, usaremos el módulo «dataframes» de «scikit learn» el cual cuenta con una serie de dataframes de ejemplo para practicar con ellos. Concretamente usaremos uno en el que se muestran los distintos atributos y componentes del vino y sus proporciones:

Como se ve, lo primero que hacemos aquí (después de hacer las importaciones pertinentes) es cargar la información de los ingredientes del módulo «datasets«, almacenándola en la variable «wines» para después, crear el correspondiente «dataframe» (con la función «DataFrame()» que ya hemos visto en otras ocasiones) que guardaremos en «df_wines«. Una vez hecho esto, mostraremos la información de la tabla sabiendo que podemos utilizar las funciones «.tail()» y «.head()» para mostrar los últimos y los primeros valores de la misma, respectivamente:

Una vez obtenidos los datos, podemos calcular la correlación entre estos usando la función «.corr()«:

OUTPUT:

Obtendremos así una tabla en la que en un rango de entre -1 y 1, se mostrará la correlación entre los distintos ingredientes.

Ya tenemos las correlaciones entre variables. No obstante, estas se pueden apreciar mejor con la ayuda de un mapa de calor, el cual, podemos generar con la ayuda de la librería «matplotlib«:

Aquí hemos empezado creando la figura de nuestra gráfica, especificando las dimensiones de la misma, así como los valores máximo («vmax«) y mínimo («vmin«) de los valores a representar, que tal y como hemos dicho son 1.0 y -1.0 respectivamente. A continuación llamamos a la función «colorbar()» para mostrar la escala de colores junto al gráfico, para después definir los elementos de los ejes ‘x’ e ‘y’ especificando una rotación de 90 grados para el primero. La ejecución de estas líneas deberá mostrar una gráfica tal como la que sigue:

Aún así, si las distintas intensidades de color en la gráfica no fueran suficientes para expresar de forma clara el nivel de correlación existente, podemos introducir en cada recuadro, el valor numérico de cada uno. Para ello nos ayudaremos de dos bucles «for» (uno anidado en el otro) con el que iremos recorriendo todas las filas y columnas de la gráfica definiendo el correspondiente valor a mostrar:

OUTPUT:

Y de este modo hemos visto la manera en la que podemos calcular la correlación existente entre las variables de un dataframe, para después graficarlas usando un mapa de calor generado con la librería «matplotlib«.

En el siguiente enlace podréis consultar la información básica referente al dataset utilizado, así como la referente a los otros que ofrece el módulo «datasets» de «scikit learn«:

https://scikit-learn.org/stable/datasets/toy_dataset.html

Saludos.