Cambiar el nombre a una columna con Pandas

logo python

Las vías que conozco,  para cambiar el nombre a una columna son tres . Podemos hacerlo con el método rename(), el cual puede aplicarse directamente a la columna, o pasarlo a través de una funcion lambda.

Ojo, es posible que haya más posibilidades, me refiero a las que uso y conozco.

Cambiar el nombre a una columna con Pandas

El método rename(),  se utiliza justo para modificar la etiqueta de los ejes, al aplicarlo nos devolverá un nuevo dataframe con los valores aplicados. Su sintaxis es:

dataframe.rename(mapper=None, index=None, columns=None, axis=None, copy=True, inplace=False, level=None, errors='ignore')

maper: Ya sea un diccionario o una función , indica las transformación a aplicar  al eje dado. Este parámetro y el eje se emplean para indicar que valores y ejes recibirán el cambio.

index: Nos permite establecer el eje. Si empleamos maper, index =0 , es lo mismo que maper = index

columns: Indica las columnas, si su valor es cero o se ignora, significa que es el mismo que maper.

axis: tiene por defecto el valor 0, que indica el índice, el valor 1 indica columnas. Pueden emplearse colocando el nombre del eje(índice, columnas), o el numero (0,1). El valor que recibe por defecto es el del índice.

copy: Su valor determinado es True, y esto garantiza copiar también los datos subyacentes.

inplace: valor por defecto False, si se convierte a True, al devolver el nuevo dataframe la copia anterior se ignora.

level: valor por defecto None, indica el numero o nombre del nivel. Si existen índices multiples solo modificara en el nivel indicado.

error: acepta raise o ignore, y ese último es su valor por defecto. Ignora el error del tipo keyerror, cuando index o columns contienen etiquetas que no existen.

Tenemos el siguiente dataframe:

Aplicándolo directamente seria algo asi:

Renombramos varias columnas usando mapping en las columnas Unnamed: 0 e Ischaemic heart disease, para ello pasamos los valores nuevos, en forma de diccionario.

Renombremos ahora los indices

Esto también podría lograrse escribiendo

data_df.rename({0: 'Año1', 1: 'Año1', 2: 'Año3'}, axis='index')

Incluso podemos cambiar el estilo :

A través de una función lambda:

Y esto es todo

Espero modestamente que este artículo, sirva de ayuda a alguien.

Gracias

…. hay que levantarse cada mañana con una esperanza y dormirse cada noche con una meta….

Y

Análisis de regresión simple.Python

logo python

En este post realizaré un análisis de regresión, en el que tomaremos una set de datos preparado previamente.

El problema real al que nos enfrentamos, es determinar la relación que pueda existir entre la cantidad de ventas de la empresa “El Dorado”, y el numero de vendedores que la han integrado durante el periodo que se estudia, que son 36 meses o sea los últimos 3 años.

El departamento ha cambiado de responsable en varias ocasiones, y cada uno ha aplicado políticas diferentes de ventas, algunas intensivas, buscando mayor productividad en las ventas, a bases de estímulos como bonos, primas, ascensos,  etc; y en otras ocasiones, en cambio,  se han aplicado medidas extensivas incrementando el numero de vendedores, en una afán por ampliar la cobertura de ventas.

Lo que vamos a hacer es implementar un análisis de regresión lineal.

La regresion lineal es una técnica estadística, que el machine learning adoptó y que incluye como uno de los algoritmos supervisados.

He escrito hace unos meses algún articulo sobre regresion lineal y resumiendo lo que hara este análisis es obtener una recta que se acerque lo mas posible a todos los puntos de datos representados en un plano.

En nuestro caso es una regresion simple (participan dos variables ) y la recta que buscamos obtener es, la mejor posible.

Esto quiere decir que de todas las rectas esta sea la que mejor se adapte al conjunto de puntos, lo que le permitirá tendencialmente  estimar o predecir valores, dentro del contexto de datos estudiados.

La recta tiene forma esta forma Y = mX + b;  donde Y es el resultado obtenido, X es la variable, m la pendiente (o coeficiente) de la recta y b el valor constante, que gráficamente expresa el “punto donde cuando X tiene valor cero, se produce la intercepción o corte con el eje Y.

 Su optimización o ajuste se logra aplicándole una función llamada de mínimos cuadráticos, o también conocida de error cuadrático.

Su nombre obedece a que esa funcion intenta minimizar el error existente entre los puntos o dados y los obtenidos, elevendo al cuadrado sus valores para evitar que se anulen.

De este modo el algoritmo, se centra en minimizar el coste de dicha función

Recordemos que los algoritmos de Machine Learning Supervisados, aprenden por sí mismos.

Utilizaremos un archivo de datos que ya tenemos, y que muestra el número de  ventas y vendedores por meses; o sea tendremos dos columnas: vendedores y ventas.

Y nuestro en nuestro análisis de regresión, lo que vamos a intentar  es determinar a partir de los vendedores que tenemos,  que valor podemos esperar en la ventas de acuerdo, a la relación dada entre ambas variables.

Trabajaremos con Jupiter Notebook,utilizaremos las librerías Pandas, SkLearn, Seaborn, Numpy, de modo que comenzaremos por ahí.

Importamos las librerías

Cargamos nuestro archivo en un dataset de pandas después de leerlo, definiendo el separador de columnas.

Adquirimos  la información de nuestro dataset, con el método info(). Observamos que tenemos dos tipos de datos : enteros en columna vendedores y decimales en la columna ventas.

Comprobamos la estructura del dataset, con el método shape, que nos dice que tenemos efectivamente dos columnas y 36 registros en cada una.

Con head(), visualizamos las 6 primeras filas de nuestro dataset

Convertimos por comodidad la columna venta a tipo entero, empleando el método astype() y guardamos esa transformación en un nuevo dataset, que es con el que continuaremos trabajando.

Definimos con columns(), los encabezados de las columnas

Obtenemos los valores estadísticos de nuestro dataset con el método describe()

Observamos entre otros valores,  que la media de vendedores es 23, con una desviación de 4,63; mientras que la de ventas es 42 millones y su desviación es de 7.12.

Visualizamos los datos, en gráficos, mostrando las columnas por separados

Empleando scatter mostramos  los puntos coloreados, separando los colores a partir de la media de vendedores (23)

En este punto creamos nuestra recta de regresion y visualizamos los coeficientes que la componen nuestra recta.

Nuestro error cuadrático no es elevado pero es alto y nuestra varianza esta más cerca de 0 que de 1, por lo que este modelo tal vez podría mejorarse.

La intersección (b), tiene un valor de 9,67…. donde se corta la recta cuando el valor en X es 0

En función de observar el comportamiento del modelo, asignamos valores diferentes para ver su comportamiento

Ahora visualicemos la recta dentro de nuestro gráfico

Podemos observar nuestros datos de diferentes formas, en este caso con la librería seaborn, vemos el comportamiento de los datos en los diferentes periodos y su relación.

Para mejorarla tenemos varios caminos, podemos aplicar métodos como el gradiente, podemos hurgar en los datos y añadir más variables predictivas, referidas por ejemplo a la competencia, la innovación o la aceptación de los productos, pasando de una regresión simple a una regresión múltiple, podríamos también ampliar la cantidad de registros buscando mas años, desechar los valores extremos, etc.

En otros artículos iré aplicando algunos de estos métodos, haciendo referencia a estos mismos datos.

Espero modestamente que este artículo, sirva de ayuda a alguien.

Gracias

«El amor es la guerra perdida, entre el sexo y la risa»

R.Arjona

Redondear decimales en Pandas con round y decimal

En esta ocasión hablare del uso de round() y decimal().

Ya en antes, he hablado, de lo que significa, y cómo aplicar el redondeo de la mejor forma posible en Python.

Sabemos, que existen múltiples ocasiones, en las que podemos necesitar sustituir un valor de tipo entero, por otro con una cantidad de decimales dada;  o directamente asignar solo una cantidad de decimales a todos los valores dentro de una dataframe.

Veamos un ejemplo para mostrar las diferentes opciones.

Primero importamos las librerías.

Importamos el dataframe

Usando round() en Pandas

Es una función que  redondea un número de coma flotante, al número de lugares decimales proporcionados como segundo argumento de la función.

Su sintaxis es round(value, numero de decimales)

En este ejemplo redondeamos la columna 2 de un dataframe

Primero aplicamos la función series() de Pandas, definimos la función round() con los espacios que deseamo, para luego aplicar un bucle for, para recorrer la columna.  

En este caso la labor de round(), es colocar una coma flotante, y dejar la cantidad de decimales que le indicamos al redondear, como segundo parámetro.

Format() como apoyo

Otra forma, es utilizar format(), pero como su nombre indica, por si sola, no redondea, sino que formatea la salida de la cadena, dandole la estructura que deseamos.

format() es una propiedad de string, o sea trabaja con una cadenas, y por lo tanto no debe confundirse con valores numéricos

La sintaxis es algo como lo que sigue, cuando la usamos en solitario, aunque existen multiples combinaciones para aplicar formato.

En este caso estamos formateando la salida de un valor a porcentaje con solo dos decimales.

df['columna3'] = pd.str(["{0:.2f}%".format(val * 100) for val in df[' columna3']])

El formato de cadena le permite representar los números como desee. Puede cambiar el número de lugares decimales que se muestran cambiando el número antes de la f.  

Usando Decimal

Cuando necesitamos una adecuada precisión es recomendable usar decimal, ya que es mucho mas adecuado que round(), si buscamos exactitud.

Puedes ver este articulo sobre la diferencia entre round() y decimal()

La construcción de la sintaxis es como se ve en el ejemplo:

En el primer caso, solo ejecutamos una división, donde obtenemos un número de coma flotante.

En los ejemplos siguientes, lo que hacemos en indicarle a Python que estamos esperando un resultado en formato decimal.

En el segundo tomamos algunas de las propiedades del contexto y le decimos a Decimal que tipo de redondeo queremos.

En el tercer y ultimo calculo, solo tomamos el contexto predeterminado e indicamos el nivel de precision que deseamos.

En todos los casos hemos redondeado a dos espacios pero podríamos haber fijado cualquier cantidad de dígitos, que necesitáramos.

..se me ha olvidado ya el lugar de donde vengo, y puede que no exista el sitio adonde voy…

J.Sabina

Pickle. serializar datos con Python

logo python

Al manejar datos, de gran volumen, que necesitamos por ejemplo guardar en archivos, para manejarlos con mayor facilidad, lo màs adecuado es serializarlos. 

El modulo pickle de Python, de que hablaré en ese post,  lo que hace es, serializar objetos para que puedan guardarse en un archivo y tener la opción de volver a cargarlos más adelante.

pickle() se utiliza para serializar y deserializar estructuras de objetos de Python,  esta acción es también conocida cómo clasificación o aplanamiento de los datos.

La serialización, en su explicación más simple no es otra cosa que  convertir un objeto que tenemos en la memoria, en un flujo de bytes que se puede almacenar en el disco o enviar a través de una red,  y que puede ser posteriormente recuperado, transformándolo nuevamente en un objeto Python deserializado.

Las ventajas de serializar nuestros datos, no es solamente que se puedan guardar en el disco para continuar trabajando con ellos, y que podamos también enviar nuestros datos a otros por TCP, o una conexión de socket.

Pickle es igualmente poderosa porque a través de ella podemos almacenar objetos de Python en una base de datos.

Sobre todo cuando trabajamos con algoritmos de aprendizaje automático, conocer su uso nos evitará tener que reescribir todo o entrenar el modelo nuevamente, ya que podemos guardarlos y recuperarlos cuando queramos.   

Datos

Pickle(), nos permite  serializar los siguientes datos:

Cadenas,

Listas,

Tuplas

Enteros

Flotadores

Booleanos,

Números complejos,

Diccionarios que contienen objetos serializables.

Dataframes

 Pickle(), también puede serializar las clases y funciones, incluso las lambdas.  En el caso de estas últimas se usa dill(), un paquete adicional diseñado para ello, a partir de un fork de multiprocessing(), el paquete de multiprocesamiento de Python

A pesar de su capacidad, elementos como los dict predeterminados, las clases internas, o los generadores pueden tener problemas para ser serializados.

Los dicts predeterminados, necesitan ser creados con una función a nivel de módulo.

Serializando archivos

Importamos pickle()  

import pickle

Creamos un diccionario  y luego estructuramos un archivo de salida llamado alumnos_dic.

#escribimos un diccionario sencillo
alumnos_dict = {'Jose': 7,'Arnoldo': 8,'Mario': 5, 'Maria': 78,'Amara': 50,'Rolando': 67,'Hemeregildo': 78,'Prudencio': 79,'Zoraida': 0}

Abrimos un archivo utilizando la función open(), para poder escribirlo en formato binario. En este articulo, puede leerse un poco mas sobre las opciones para usar open().

#abrimos nuestro archivo para escribir en formarto binario
alumnos_pick= open('alumnos', 'wb')

Serializamos el archivo inicial y obtenemos un nuevo objeto file, luego cerramos la conexión

#usamos dump para serializar
pickle.dump(alumnos_dict, alumnos_pick)
alumnos_pick.close()

Deserializar nuestro archivo

El proceso de volver a cargar un archivo serializado en Python, no es complejo.

Usaremos la función open () nuevamente, pero esta vez con 'rb' como segundo argumento.

alumnos_pick.close()

Lo que haremos será leer el formato binario con que serializamos anteriormente.

#usamos dump para serializar
pickle.dump(alumnos_dict, alumnos_pick)
alumnos_pick.close()

Asignamos su valor  a infile.

infile = open('alumnos','rb')

Para cargar el archivo utilizamos pickle.load (), con infile como argumento, al que asignaremos  a nuevo_alumnos.

nuevo_alumnos = pickle.load(infile)

El contenido del archivo ahora está asignado a esta nueva variable.

Nuevamente,  cerramos  el archivo al final.

infile.close()
nuevo_alumnos
output:{'Jose': 7, 'Arnoldo': 8, 'Mario': 5, 'Maria': 78, 'Amara': 50, 'Rolando': 67, 'Hemeregildo': 78, 'Prudencio': 79, 'Zoraida': 0}

Comparamos los archivos.

#comparamos ambos archivos
print(nuevo_alumnos==alumnos_dict)
print(type(nuevo_alumnos))
output: True 
<class 'dict'>

Comprimir archivos

Si el tamaño del archivo es grande, por ejemplo datasets, voluminosos, podemos ahorrar espacio comprimiendo, el archivo deserializado.

Hay diferentes vías, dos de ellas son bzip2 y gzip.  Puede ver otras en este articulo.

Su diferencia en esencia, radica en que  gzip  es más rápido, pero los archivos que crea bzip2, ocupan  la mitad de espacio que los que crea gzip.

Una cuestión importante y que puede tender a confundir es que deserializar, no es lo mismo que comprimir.  

La deserialización es la conversión de un objeto de una representación (datos en la memoria de acceso aleatorio (RAM)) a otra (texto en el disco); mientras que la compresión es el proceso de codificación de datos con menos bits, para ahorrar espacio en el disco.

Lo primero es importar bz2

import bz2

Luego como primer parámetro del método BZ2File, pasaremos el nuevo nombre del nuevo archivo compactado que se creará al ejecutarse el script

sfile = bz2.BZ2File('compress_alumnos', 'w')
pickle.dump(alumnos_dict, sfile)

Multiproceso

Pickle es especialmente sensible al multiprocesamiento, pues hay elementos como las funciones lambda que no pueden ser fácilmente serializadas.

Cuando necesitamos realizar tareas complejas que ocupan mucho espacio de memoria, es común distribuir esta tarea en varios procesos.

El multiprocesamiento, es la subdivisión de un proceso en varios que se ejecutan simultáneamente, generalmente en varias Unidades Centrales de Procesamiento (CPU) o núcleos de CPU, ahorrando tiempo, como es el caso de operaciones de entrenamiento de modelos de aprendizaje automático, la creación de redes neuronales, todos ellos procesos intensivos.

En Python, esto se hace usando el paquete de multiprocesamiento multiprocessing().

La ventaja de trabajar de esta forma, es que los procesos en que se divide una tarea no comparten espacio de memoria, y comparten datos entre ellos serializados 

En el ejemplo lo que haremos será crear una especie de abstracción llamada pool, para que trabaje en segundo plano procesando una tarea, y al que indicaremos cuantos procesadores empleará para ello.

#trabajando con multiprocesamiento
#importamos el modulo y creamos con la la funcion cos una tarea
import multiprocessing as mp
from math import cos
p = mp.Pool(2)
p.map(cos, range(10))
output:[1.0, 0.5403023058681398, -0.4161468365471424, -0.9899924966004454, -0.6536436208636119, 0.2836621854632263, 0.9601702866503661, 0.7539022543433046, -0.14550003380861354, -0.9111302618846769]

Si quisiéramos ejecutar en vez de cos() un lambda, nos lanzara un error, indicando que Pickle no puede serializar un lambda.

p.map(lambda x: 2**x, range(10))
output: .......
PicklingError: Can't pickle <function <lambda> at 0x7fe84683a830>: attribute lookup <lambda> on __main__ failed

Afortunadamente existe un modulo para resolver esto dill(), que pertenece a un fork, llamado pathos.multiprocessing

Pathos esta en desarrollo aun, y debe ser instalado desde github, según recomendaciones de su creador. Puedes ver este articulo en stackoverflow

El amor siempre empieza soñando y termina en insomnio

R.Arjona

Trabajando con el modulo re() de Python

logo python

Python tiene un módulo llamado re para trabajar con las RegEx.

Pueden ver un articulo que escribí hace un tiempo, sobre ello.

En Python, existen herramientas especificas, que funcionan como auxiliares y modificadores para el trabajo con las RegEx.

Me refiero tanto al uso del modulo re() , como al empleo de r o R antes de una RegEx como prefijo.

Cuando se escribe una expresión regular y se coloca el \ delante de ella, este equivale a un escape del carácter que le sigue, de este modo \n o \r provocará que el lenguaje escape estos caracteres; sin embargo cuando colocamos r delante, estos serán considerados y tratados como un carácter normal.

La sintaxis para esto, es por ejemplo r’[\n\r]’

Veamos como usar re()

re.findall()

Nos devuelve una lista de todas las cadenas que contienen la coincidencias

import re

cadena = 'Cuanto hice hasta hoy, y haré, es para eso. En silencio ha tenido que ser y como indirectamente, porque hay cosas que para lograrlas han de andar ocultas, y de proclamarse en lo que son levantarían dificultades demasiado recias para alcanzar sobre ellas el fin.'
pattern = '\D+'
buscamos todos aquellos caracteres que no sean digitos con re.findall()
coincid = re.findall(pattern, cadena)
coincid
ouput:['Cuanto hice hasta hoy, y haré, es para eso. En silencio ha tenido que ser y como indirectamente, porque hay cosas que para lograrlas han de andar ocultas, y de proclamarse en lo que son levantarían dificultades demasiado recias para alcanzar sobre ellas el fin.']

pattern = '\d+'
output:[]

re.split()

Separa las cadenas donde existen las coincidencias y retorna una lista de  cadenas donde hay coincidencias.

pattern = '\D+'
cadena = 'amigos 12345 45:67'
#separamos las palabras de la cadena con re.split()
coincid = re.split(pattern, cadena)
coincid
output: ['', '12345', '45', '67']
pattern = '\d+'
output:cadena = 'amigos 12345 45:67'

#separamos las palabras de la cadena con re.split()
coincid = re.split(pattern, cadena)
coincid
output:['amigos ', ' ', ':', '']

Como se ve en el ejemplo se puede usar maxsplit para determinar el numero máximo de separaciones que deseamos que ocurran.

#utilizamos maxsplit 1
pattern = '\D+'
cadena = 'amigos 12345 45:67'
coincid = re.split(pattern, cadena, 1)
coincid
output:['', '12345 45:67']

#utilizamos maxsplit 3
pattern = '\D+'
cadena = 'amigos 12345 45:67'
coincid = re.split(pattern, cadena, 3)
coincid
output:['', '12345', '45', '67']

Re.sub()

Devuelve la cadena donde existe coincidencia y reemplaza el contenido con el valor de la variable replace.

#sustituimos en la cadena los valores con re.sub()
cadena = 'Cuanto hice hasta hoy, y haré, es para eso. En silencio ha tenido que ser y como indirectamente, porque hay cosas que para lograrlas han de andar ocultas, y de proclamarse en lo que son levantarían dificultades demasiado recias para alcanzar sobre ellas el fin.'
pattern = '\s+'
replace = ','
nueva_cadena = re.sub(pattern, replace, cadena)
nueva_cadena
out:'Cuanto,hice,hasta,hoy,,y,haré,,es,para,eso.,En,silencio,ha,tenido,que,ser,y,como,indirectamente,,porque,hay,cosas,que,para,lograrlas,han,de,andar,ocultas,,y,de,proclamarse,en,lo,que,son,levantarían,dificultades,demasiado,recias,para,alcanzar,sobre,ellas,el,fin.'

Podemos contar  utilizando count() como cuarto parámetro, para determinar cuántos reemplazosharenmos.

Si omitiéramos el valor sub(), reemplazará todas las coincidencias.

#añadiendo count() como parametro
string = 'Cuanto hice hasta hoy, y haré, es para eso. En silencio ha tenido que ser y como indirectamente, porque hay cosas que para lograrlas han de andar ocultas, y de proclamarse en lo que son levantarían dificultades demasiado recias para alcanzar sobre ellas el fin.'
pattern = '\s+'
replace = ','
nueva_cadena = re.sub(pattern, replace, string, 5)
nueva_cadena
output:'Cuanto,hice,hasta,hoy,,y,haré, es para eso. En silencio ha tenido que ser y como indirectamente, porque hay cosas que para lograrlas han de andar ocultas, y de proclamarse en lo que son levantarían dificultades demasiado recias para alcanzar sobre ellas el fin.'

re.subn()

Es similar a sub(), pero devuelve una tupla con contiene la nueva cadena y la cantidad de sustitucones realizadas.

#empleamos re.subn(), para obgener una tupla que contiene la nueva cadena y la cantidad de substituciones realizadas
cadena = 'Cuanto hice hasta hoy, y haré, es para eso. En silencio ha tenido que ser y como indirectamente, porque hay cosas que para lograrlas han de andar ocultas, y de proclamarse en lo que son levantarían dificultades demasiado recias para alcanzar sobre ellas el fin.'
pattern = '\s+'
replace = ','
nueva_cadena = re.subn(pattern, replace, cadena)
nueva_cadena
output: ('Cuanto,hice,hasta,hoy,,y,haré,,es,para,eso.,En,silencio,ha,tenido,que,ser,y,como,indirectamente,,porque,hay,cosas,que,para,lograrlas,han,de,andar,ocultas,,y,de,proclamarse,en,lo,que,son,levantarían,dificultades,demasiado,recias,para,alcanzar,sobre,ellas,el,fin.', 44)

re.search()

Se emplea para la búsqueda de coincidencias directamente, utilizando dos argumentos, el patrón a buscar y la cadena donde buscarlo.

Su resultado es un objeto match, si no hubiera coincidencia retornaría None.

#empleamos re.search(), para hallar la subcadena silencio
sustituimos en la cadena los valores con re.sub()
cadena = 'Cuanto hice hasta hoy, y haré, es para eso. En silencio ha tenido que ser y como indirectamente, porque hay cosas que para lograrlas han de andar ocultas, y de proclamarse en lo que son levantarían dificultades demasiado recias para alcanzar sobre ellas el fin.'
busqueda = re.search('silencio',cadena)
busqueda
output:<re.Match object; span=(47, 55), match='silencio'>

El objeto que nos devuelve la variable búsqueda es del tipo match, con el cual podemos hacer también varias operaciones.

#operando con el resultado, ahora buscamos silencio al final de una cadena y hacemos algo
adena = 'Cuanto hice hasta hoy, y haré, es para eso. En silencio ha tenido que ser y como indirectamente, porque hay cosas que para lograrlas han de andar ocultas, y de proclamarse en lo que son levantarían dificultades demasiado recias para alcanzar sobre ellas el fin.'
busqueda = re.search('\Zsilencio',cadena)
if busqueda:
pass
else:
print('no se halló nada')
output:no se halló nada

Con re(), podemos buscar utilizando re.match(), que  recibe dos parámetros: los patrones que buscamos y el texto donde los buscamos.

match.group()

Nos permite agrupar los resultados en subcadenas.

#buscamos con match.group() el grupo de letras seguidas por una r
cadena = 'Cuanto hice hasta hoy, y haré, es para eso. En silencio ha tenido que ser y como indirectamente, porque hay cosas que para lograrlas han de andar ocultas, y de proclamarse en lo que son levantarían dificultades demasiado recias para alcanzar sobre ellas el fin.'
pattern = '(a|e|i)r'
match = re.search(pattern, cadena)
if match:
print(match.group())
else:
print('no se halló nada')
output:ar

#buscamos un grupo que tiene dos digitos separados por un espacio de una cadena no digital de seis caracteres
cadena = '234 567896 10 acceso dni color de los ojos'
pattern = '(\d{2}) (\D{6})'
match = re.search(pattern, cadena)
if match:
print(match.group())
else:
print('no se halló nada')
output: 10 acceso

Podemos condicionar cuantas subcadenas queremos y sus posiciones

#imprimiendo solo el primer subgrupo
match = re.search(pattern, cadena)
if match:
print(match.group(1))
else:
print('no se halló nada')
output:10

#obteniendo la posicion donde comienza el grupo, donde termina y una tupla con ambos valores
match = re.search(pattern, cadena)
if match:
print(match.start(), match.end(), match.span())
else:
print('no se halló nada')
output:11 20 (11, 20)

Match.string

Nos devuelve la cadena.

match.string
output:'234 567896 10 acceso dni color de los ojos'

«En total oscuridad cualquier cosa, puede ser luz»

TypeError: ‘Index’ object is not callable

logo python

Si ante recibes este error al escribir esto en Pandas:

data_df.columns()

Se debe a que están intentado llamar el método de modo incorrecto.

Es un error común de principiante, porque intentas obligar a Pandas a que use cómo índice el propio índice que el establece.

El objeto index no puede llamarse , porque no es un atributo del dataframe, entonces no puede llamarlas de ese modo, según el concepto de la librería.

Por la misma causa podrías recibir el error SyntaxError: invalid syntax

Solución

data_df.columns

Espero modestamente que este artículo, sirva de ayuda a alguien.

Gracias

«Sin   herramientas para imaginar tu secreto…..»

Y

Recuperar una imagen en Django, dinámicamente.

logo django

Cuando trabajamos en Django, es común colocar el avatar de nuestro usuario en el panel, si tenemos habilitado nuestro modulo "context_procesor", dentro de templates en nuestro archivo setting.py., podemos seguir las instrucciones siguiente.

Como recuperar una imagen en Django dinámicamente.

El código para llamar a nuestra imagen podría ser este:

<img src='{{user.avatar.url }}'
alt="{{user.username }}" 
class="class="img-fluid  user_imag rounded-circle">

Si el modulo no estuviera habilitado debemos incluirlo

TEMPLATES = [
 {
    'BACKEND': 'django.template.backends.django.DjangoTemplates',
    'DIRS': [],
    'APP_DIRS': True,
    'OPTIONS': {
        'context_processors': [
        'django.template.context_processors.debug',
        'django.template.context_processors.request',     #modulo
        'django.contrib.auth.context_processors.auth',
        'django.contrib.messages.context_processors.messages',
            ],
         },
      },
]

La magia está, en que el método request(), nos traerá la instancia del user a toda pagina que tengamos, por tanto dispondremos de sus atributos, para el usuario visitante.

Recuperando una imagen en el html

Suponiendo que hemos creado nuestro modelo, nuestro form y nuestras url, podemos recuperar a nuestra imagen con

{% for a in object_list  %} 
<section class="dashboard-header section-padding" style=" border:2px solid blue; margin-bottom:15px;">
  <div class="container-fluid">
    <div class="col-lg-3" >
      <img  src='{{a.profile.photouser.url}}'  alt="{{a.user.username}}" class="img-fluid  user_imag rounded-circle">
    </div> …….
 </section>
 {% endfor %} 
  

…. hay que levantarse cada mañana con una esperanza y dormirse cada noche con una meta….

Espero que sirva de ayuda a alguien

Usando hashlib en Python

logo python

Python nos ofrece multiples librerías con valor incalculable para todo el tema de criptografía, una de ellas la librería hashlib, que nos va a permitir trabajar con un tipo de encriptado conocido como SHA

Su nombre proviene del inglés, ( Secure Hash Algorithms ), y su labor consiste en crear estructuras seguras, mediante funciones de encriptado, que puedan ser utilizados por diferentes lenguajes de modo transversal.

Los algoritmos o funciones SHA con que trabaja haslib, son varios(‘sha256', 'sha384', 'sha224', 'sha512', 'sha1'), con diferentes tamaños de bloque

hashlib, posee dos funciones asociadas, que usaremos al aplicar las transformaciones:

  • encode() : Convierte las cadenas en bytes, para que la funcion hash pueda procesarla.
  • hexdigest() : Devuelve el dato codificado en formato hexadecimal.

Haremos una pequeña demostración de su uso:

Introduciremos un cadena  y la convertiremos a su equivalencia en bytes utilizando la funcion enconde(),  para que la funcion SHA  pueda manipularla, esta la codifica con hexdigest(), e imprimimos la cadena resultante

import hashlib 
import hashlib 
   
 # valor de entrada 
 str = "el comienzo de todo"
   
 result = hashlib.sha256(str.encode()) 
  
 # Imprimiendo el valor hexadecimal. 
 print("El resultado es: ") 
 print(result.hexdigest()) 
 print ("\r") 
  
 # salida: El resultado es: 
 9f78aef8f9e252913e43156c570568592f014cb0175d52a6071a5eed8959e183
    
   
 # valor de entrada 
 str = " el comienzo de todo "
  
 result = hashlib.MD5(str.encode()) 
   
 # Imprimiendo el valor hexadecimal. 
 print("El resultado es: ") 
 print(result.hexdigest())
 # salida: El resultado es: 3455ed58e2999e23fc7385207e4fb999 

Y listo esto es todo.

Espero modestamente que este artículo, sirva de ayuda a alguien.

Gracias.

…. hay que levantarse cada mañana con una esperanza y dormirse cada noche con una meta….

TypeError: argument of type ‘NoneType’ is not iterable. Python

logo python

Este error que Python lanza, obedece, según mi experiencia, a casos en que una función con una declaración  condicional (if, else, case, etc) no devuelve un resultado o lo  devuelve vacío.

Si esto sucede, Python devuelve un valor por defecto que es None, el cual no es iterable, por tanto en la próxima iteración lanzara un error.

La solución a esto, es detener la iteración en casos donde pueda haber un valor vacío (por ejemplo utilizando break), o añadiendo acciones (por ejemplo con while), de modo que se solucione o detenga la iteración.

«Puedo absorber tus pecados, pero no vivir tu vida.»

Y

Espero modestamente que este artículo, sirva de ayuda a alguien.

Gracias