Mostrando entradas con la etiqueta in. Mostrar todas las entradas
Mostrando entradas con la etiqueta in. Mostrar todas las entradas

sábado, 3 de abril de 2021

Las Tuplas en Python



Las Tuplas son uno de los cuatro tipos de datos que podemos encontrar en Python, lo otros tres son las listas, los conjuntos y los diccionarios.

Son un tipo de dato inmutable, lo que significa que una vez creadas no se pueden cambiar, añadir o eliminar elementos. Por contra si son iterables, es decir permiten recorrerlas y sus datos están ordenados.

Las tuplas se escriben entre paréntesis (), aunque una sucesión de elementos asignados a una variable, aunque no lleven paréntesis, también se consideran como una tupla.

>>> tupla1 = ('a',4,'cuadrado')
>>> tupla2 = 'a', 4, 'cuadrado'
>>> print(type(tupla1), type(tupla2))
<class 'tuple'> <class 'tuple'>

Sin embargo, tienes que tener en cuenta que para crear una tupla con un solo elemento tienes que añadir una coma después del elemento ya que sino Python no lo considerará como otro tipo de dato.

>>> estoesunaTupla = ("manzana",)
>>> print(type(estoesunaTupla))
<class 'tuple'>

#No es una Tupla
>>> EstaOtra = ("manzana")
>>> print(type(EstaOtra))
<class 'string'>


Existen constructores para convertir las listas en tuplas y viceversa. Para convertir algo en una tupla podemos usar el constructor tuple().

>>> miLista=[1,2,3]
>>> miTupla=tuple(miLista)
>>> print(miTupla)
(1, 2, 3)


Comandos útiles para trabajar con Tuplas u otras secuencias.


.count()        

Usamos este método para determinar cuantas veces un elemento se encuentra dentro de una Tupla.

>>> mi_tupla = 1, 5, 6, 1, 0, 3, 2, 1
>>> print(mi_tupla.count(1))
3


len()

Usamos la función len() para determinar el número de elementos hay en una tupla.

>>> mi_tupla = 1, 5, 6, 1, 0, 3, 2, 1
>>> print(len(mi_tupla))
8


in 

Usamos el comando in, que tambien vimos en las listas, para determinar si un elemento esta en la tupla.

>>> mi_tupla = 1, 5, 6, 1, 0, 3, 2, 1
>>> print(1 in mi_tupla)
True
>>> print(9 in mi_tupla)
False


not in

Usamos el comando not in, que también vimos en las listas, para determinar si un elemento no esta en la secuencia.

>>> mi_tupla = 1, 5, 6, 1, 0, 3, 2, 1
>>> print(1 not in mi_tupla)
False
>>> print(9 not in mi_tupla)
True


secuencia1 + secuencia2

Podemos unir varias secuencias, en este caso tuplas, usando el operador +

>>> tupla1 = 1,2,3
>>> tupla2 = 4,5,6
>>> tupla3 = tupla1 + tupla2
>>> print(tupla3)
(1, 2, 3, 4, 5, 6)


enumerate(secuencia, <nº inicio=0>)

Crea un objeto en el que cada uno de los elementos de la secuencia esta enumerado. Si no especificamos el número de inicio, que es opcional, comienza en el 0.

>>> tupla1 = 'patata'
>>> print(tuple(enumerate(tupla1)))
((0, 'p'), (1, 'a'), (2, 't'), (3, 'a'), (4, 't'), (5, 'a'))


.index()

Usamos el método index para saber la posición de un elemento dentro de un iterable, en este caso, una tupla. Recuerda que los elementos se empiezan a contar en el cero.

>>> mi_tupla = 1, 5, 6, 1, 0, 3, 2, 1
>>> print(mi_tupla.index(5))
1


zip()

Genera un objeto con la unión de secuencias con elementos que ocupan la misma posición. Veámoslo con un ejemplo uniendo dos tuplas.

>>> t1 = ('p','t','t')
>>> t2 = ('a','a','a')
>>> t3=zip(t1,t2)
>>> print(t3)
<zip object at 0x7f3bb9d6ce80>
>>> print(tuple(t3))
(('p', 'a'), ('t', 'a'), ('t', 'a'))

Podemos aplicar a las Tuplas otras funciones que vimos en las listas como min(), max(), sum().


Como acceder a los elementos de una Tupla.


Podemos acceder a los elementos de una Tupla indicando su posición dentro de corchetes [].

>>> mi_tupla = ('peras','platanos','manzanas')
>>> # Imprimimos las manzanas accediendo a su posición
>>> print(mi_tupla[2])
manzanas

Nota: ten en cuenta que el primer elemento tiene como indice el 0.


Índices Negativos.

Cuando usamos índices negativos significa que empezamos a contar por el final.

-1 hace referencia al último elemento, -2 al penúltimo y así sucesivamente.

>>> mi_tupla = ('peras','platanos','manzanas')
>>> # Imprimimos el penúltimo elemento de la tupla.
>>> print(mi_tupla[-2])
platanos


Rango de Índices.

Podemos especificar los elementos de un iterable especificando donde iniciar y donde terminar el rango. Al especificar un rango, el valor que se nos retorna será una nueva tupla con los valores especificados.

>>> mi_tupla = (1,2,3,4,5,6,7,8,9,10,11,12)
>>> print(mi_tupla[2:7])
(3, 4, 5, 6, 7)

 Nota: la selección comienza en el elemento con el índice 2 (incluido) y finaliza en el elemento con índice 7 (sin incluir).

Recuerda que el primer elemento tiene como índice 0.

Si no especificamos el primer valor, la selección comenzará con el primer valor:

>>> mi_tupla = (1,2,3,4,5,6,7,8,9,10,11,12)
>>> print(mi_tupla[:7])
(1, 2, 3, 4, 5, 6, 7)

Si no especificamos el valor final, la selección se extenderá hasta el final del iterable:

>>> mi_tupla = (1,2,3,4,5,6,7,8,9,10,11,12)
>>> print(mi_tupla[5:])
(6, 7, 8, 9, 10, 11, 12)


Selección con Índices Negativos:

Usamos índices negativos cuando queremos empezar la selección o rango desde el final de una tupla.

Por ejemplo:

>>> mi_tupla = (1,2,3,4,5,6,7,8,9,10,11,12)
>>> print(mi_tupla[-4:-1])
(9, 10, 11)


¿Actualizar los datos de una Tupla?

Como ya dijimos, una vez que se crea una Tupla, no podemos cambiar sus valores. Por eso se dice que son Inmutables. 

Entonces, ¿Cómo podemos cambiar sus valores? Pues no podemos hacerlo hacerlo directamente, pero si dando un pequeño rodeo. El truco está en cambiar temporalmente la Tupla a una Lista, hacer la modificación, y volver a convertirla en una Tupla. 

>>> mi_tupla=('pera','naranja','piña')>>> mi_lista=list(mi_tupla)>>> mi_lista[1]='trufa'>>> mi_tupla=tuple(mi_lista)>>> print(mi_tupla)('pera', 'trufa', 'piña')

Y tendríamos que utilizar el mismo truco si quisiéramos añadir o eliminar más elementos a la tupla una vez creada.


Empaquetado y Desempaquetado de Tuplas.


Cuando creamos una tupla y la asignamos a una variable, normalmente le asignamos unos valores, como hemos hecho hasta ahora en todos los ejemplos previos. Esto es lo que se conoce como empaquetado de Tuplas. (aunque por extensión se utiliza en todos los datos que admiten secuencias)

Pero, en Python, también podemos desempaquetar las secuencias, es decir, realizar una asignación múltiple a partir de estructuras de tipo secuencial (cadenas, listas, tuplas)

>>> numeros = (1,2,3)
>>> x, y, x = numeros
>>> print(x)
1
>>> print(y)
2
>>> print(z)
3
o

>>> lista = [('David',1),('Pepe',2),('Domitilo',3)]
>>> for x,y in lista:
>>>   print(x,y)
David 1
Pepe 2
Domitilo 3


Nota: El número de variables debe coincidir con el número de valores de la Tupla; de lo contrario debes utilizar un * para recopilar los valores restantes como una lista.

Veamos un ejemplo de una tupla que tiene más valores que las variables a las que las vamos a asignar.

>>> mi_tupla = (1,2,3,4,5,6,7,8,9,10,11,12)
>>> x, y, *z = mi_tupla
>>> print(x)
1
>>> print(y)
2
>>> print(z)
[3, 4, 5, 6, 7, 8, 9, 10, 11, 12]

Como veis la variable z recoge, en forma de lista, todos los valores que no se pueden asignar a las otras variable.

Tuplas con nombres.

Una librería útil de la biblioteca estándar de Python es collections. En ella encontramos un método útil como es namedtuple. Nos sirve para acceder a los elementos de una tupla usando un nombre en vez de como hemos visto hasta ahora, en la que accedemos a los elementos de la tupla por posición. (aunque tambien se puede seguir accediendo a los datos por posición si prefieres). Esto es muy útil porque cuando un programa es algo complejo se hace complicado recordar que posición correspondía a que dato, es más sencillo ponerles nombre. Por ejemplo, si creamos una variable llamada circulo y con una tupla le pasamos los puntos (x, y) y un radio, para acceder a sus valores haremos:

>>> circulo = (3, 4, 7)
>>> circulo[0] # x
3
>>> circulo[1] # y
4
>>> circulo[2] # radio
7
Usando las tuplas con nombre se podría hacer de las siguiente forma:

>>> from collections import namedtuple
>>> circulo = namedtuple('circulo', "x y radio")
>>> circulo1 = circulo(3,4,7)
>>> print(circulo1.x)
3
>>> print(circulo1.y)
4
>>> print(circulo1.radio)
7

Es decir usamos nametupled('nombre_subclase', "argumentos como strings  separados por espacios")

martes, 23 de marzo de 2021

Las listas en Python



una_lista = ['peras', 'manzanas', 'zanahorias']

Las Listas. 


Usamos las listas para guardar múltiples elementos en una sola variable.

Las listas son uno de los cuatro elementos que se usan para almacenar datos, los otros son las Tuplas, los Conjuntos y los Diccionarios.

Las listas se crean usando corchetes.

nombre_lista = [elemento1, elemento2,....., elemento_n]

Los elementos de una lista están ordenados, se pueden modificar y permiten valores duplicados.

Al estar ordenados podemos acceder a cualquier elemento de la lista indicando su posición en la misma. Asi empezando por la izquierda, el primer elemento tiene el indice [0], el segundo [1] y así sucesivamente. Este orden no cambia de forma que si añadimos nuevos elementos a la lista estos se situarán al final de la misma.

Veamos algunos ejemplos de como acceder a una lista usando una lista con números.

>>> lista = [1,2,3,4,5,6,7,8,9,10]
>>> # Si queremos por ejemplo imprimir el numero 4 (cuyo índice es el 3)
>>> print(lista[3])
4

Si quisiéramos imprimir toda la lista podemos usar:

>>> print(lista)
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
>>> # o también [:] lo que quiere decir que imprima desde el primer al ultimo elemento de la lista >>> print(lista[:]) [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]

Si quisiéramos imprimir o usar solo una parte o porción de la lista (Slicing o rebanadas en python), usamos la expresión:

lista[desde_posicion, hasta posición sin incluir ese elemento, salto]

>>> # Imprimir los 5 primeros números
>>> print(lista[0:5])
[1, 2, 3, 4, 5]
>>> # Imprimir desde el 6 al final.
>>> print(lista[5:10])
[6, 7, 8, 9]
>>> print(lista[5:])
[6, 7, 8, 9, 10]
>>> # Imprimir cada dos números desde el primer al ultimo elemento
>>> print(lista[::2])
[1, 3, 5, 7, 9]


También podemos indicar el índice del elemento empezando a contar desde la izquierda, en ese caso utilizaremos el índice con el signo menos y empezando por el -1 y no por el cero como hicimos antes. Podemos combinar ambas formas de indicar el índice de los elementos.

>>> # Imprimir los 5 primeros números
>>> print(lista[-10:-5])
[1, 2, 3, 4, 5]
>>> # Imprimir desde el 6 al final.
>>> print(lista[-5:10])
[6, 7, 8, 9]
>>> print(lista[-5:])
[6, 7, 8, 9, 10]
>>> # Imprimir cada dos números desde el último al primero
>>> print(lista[::-2])
[10, 8, 6, 4, 2]
>>> # Invertir el orden de los elementos de una lista.
>>> print(lista[::-1])
[10, 9, 8, 7, 6, 5, 4, 3, 2, 1]


Longitud de una lista.


Para saber cuantos elementos tiene una lista usaremos la función len()

Ejemplo

Imprimimos el tamaño o número de elementos de una lista:

>>> lista = ["manzana""platano""pera"]
>>> print(len(lista))
3


Tipos de datos que pueden formar una lista.


Los elementos que se pueden almacenar en una lista pueden ser.....CUALQUIERA. Pueden ser números, strings o cadenas de texto, booleanos o incluso una combinación de todos ellos.

lista_string = ["manzana""platano""pera"]
lista_numeros = [15793]
lista_booleanos = [TrueFalseFalse]
lista_combinada = [True, 5, "manzana"]

También puede haber una lista con otra u otras listas dentro:

>>> lista = ["manzana", "platano", "pera", [1, 2, 3, 4]]
>>> print(lista[len(lista)])
4

Como ves la lista tiene 4 elementos, los tres primeros son frutas y el cuarto es otra lista. Si queremos acceder a un elemento de esta última lista es muy sencillo. Primero indicamos su índice en la lista principal y luego otra vez el elemento al que queremos acceder dentro de la sub-lista de números. Por ejemplo para imprimir el nº 3 de la lista de números:

>>> lista = ["manzana", "platano", "pera", [1, 2, 3, 4]]
>>> print(lista[3][2])
3
# [Elemento con indice 3 de la lista principal] y [2 de la sublista]


Desde la perspectiva de Python las listas son definidas como objetos cuyo tipo de datos es "list"

>>> lista = ["manzana", "platano", "pera", [1, 2, 3, 4]]
>>> print(type(lista))
<class 'list'>


y también es posible usar el constructor "list()" para crear una lista a partir de otro tipo de objeto:

>>> palabra ="Bienvenido"
>>> print(list(palabra))
['b', 'i', 'e', 'n', 'v', 'e', 'n', 'i', 'd', 'o']


Métodos que podemos usar para trabajar con listas.


*)     nombre_lista.append(elemento)        Añade un elemento al final de la lista.

>>> lista = ['uno','dos','tres']
>>> item = 'cuatro'
>>> lista.append(item)
>>> print(lista)
['uno', 'dos', 'tres', 'cuatro']
Otra forma usando slicing de listas es la siguiente:

>>> lista = ['uno','dos','tres']
>>> item = ['cuatro']
>>> lista[len(lista):]=item
>>> print(lista)
['uno', 'dos', 'tres', 'cuatro']

Aunque quizá la forma más fácil de fusionar o añadir una lista a continuación de otra es usar las suma "+", vamos sumando ambas listas:

>>> lista = ['uno','dos','tres']
>>> item = ['cuatro']
>>> lista = lista + item
>>> print(lista)
['uno', 'dos', 'tres', 'cuatro']

y ya que estamos con los signos matemáticos si usas el signo de multiplicar con una lista la multiplicas n veces:

>>> lista = ['uno','dos'] * 3
>>> print(lista)
['uno', 'dos', 'uno', 'dos', 'uno', 'dos']


*)     nombre_lista.insert(i, item)                 Añade el item en la posición i desplazando al resto hacia la derecha.

>>> # añadimos el cuatro donde estaba el dos, es decir en la posición 1.
>>> lista = ['uno','dos','tres']
>>> item = 'cuatro'
>>> lista.insert(1,item)
>>> print(lista)
['uno', 'cuatro', 'dos', 'tres']


*)     nombre_lista.extend(otra_lista)            Fusiona o añade una lista a la anterior.

>>> lista = ['uno','dos','tres']
>>> items = ['cuatro','cinco']
>>> lista.extend(items)
>>> print(lista)
['uno', 'dos', 'tres', 'cuatro', 'cinco']

otro ejemplo:

>>> lista = [1,2,3,4]
>>> lista.extend(range(5,11))
>>> print(lista)
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]


En el ejemplo he utilizado la función range() que lo que hace es crear una lista de números secuenciales.

Su estructura es:

 range(nº inicio, nº final sin incluir, salto)


*)       nombre_lista.index(elemento)                 Nos devuelve el índice o posición del primer elemento de la lista que coincida con el elemento dado.

>>> lista = ["manzana", "platano", "pera", "platano"]
>>> print(lista.index("manzana"))
0
>>> print(lista.index("platano"))
1
>>> print(lista.index("pera"))
2


*)     nombre_lista.pop(<indice_elemento>)       Modifica la lista original, eliminando el elemento de la misma que esté en la posición indicada y lo asigna a una variable si es el caso. El argumento del método es opcional y si no pones nada se entiende que es el último elemento de la lista.

>>> lista_original = ["manzana", "platano", "pera", "platano"]
>>> lista_original.pop() # quita el ultimo elemento de la lista modificándola.
>>> print(lista_original)
['manzana', 'platano', 'pera']
x= lista_original.pop(1) # quitamos el elemento de la posición 1 y lo asignamos a x.
>>> print(x)
platano
>>> print(lista_original) # Como queda la lista después de las modificaciones.
['manzana', 'pera']


Con esto podemos utilizar cosas que se encuentran en otros lenguajes de programación como son las pilas y colas de datos. 

En las pilas se sigue el método LIFO (Last In First Out), es decir, los últimos datos que entran en las listas son los primeros en salir. Utilizaremos los métodos append() y pop(). Veámoslo con este ejemplo. Tenemos un almacén  nos traen la mercancía en cajas. Y la vamos vendiendo primero las últimas que nos traen.

>>> lista_cajas = [5,2,6,7]
>>> # Nos traen otras dos cajas y las metemos en el stock
>>> lista_cajas.append(2)
>>> print(lista_cajas)
[5, 2, 6, 7, 2]
>>> # Ahora sacamos 9 del almacén utilizando el método de la pila. (7, 2)
>>> lista_cajas.pop()
>>> list_cajas.pop()
>>> print(lista_cajas)
[5, 2, 6]


En las colas pasa lo contrario. Va saliendo de la variable primero lo que entro antes. Utilizaremos los métodos insert(0, item) y pop(). Veámoslo con un ejemplo.

>>> lista_cajas = [5,2,6,7]
>>> # Nos traen otras dos cajas y las metemos en el stock
>>> lista_cajas.insert(0, 2)
>>> print(lista_cajas)
[2, 5, 2, 6, 7]
>>> # Ahora sacamos 7 del almacén utilizando el método de la pila. (7)
>>> lista_cajas.pop()
>>> print(lista_cajas)
[2, 5, 2, 6]


*)   nombre_lista.count(item)           Cuenta las veces que un objeto está en una lista.

>>> lista=[2, 5, 2, 6, 7, 2]
>>> print(lista.count(2))
3


*) nombre_lista.remove(item)            Elimina el primer elemento que coincide de una lista.     

>>> lista=[2, 5, 2, 6, 7, 2]
>>> lista.remove(2)
>>> print(lista)
[5, 2, 6, 7, 2]


Para eliminar un elemento de una lista también podemos usar su posición con la instrucción:

del lista[indice_elemento]

>>> lista=[2, 5, 2, 6, 7, 2]
>>> # Borramos el primer 2 de la lista que ocupa la posición 0.
>>> del lista[0]
>>> print(lista)
[5, 2, 6, 7, 2]


 *)  nombre_lista.clear()            Vacía la lista de elementos.

>>> lista=[2, 5, 2, 6, 7, 2]
>>> # Vaciamos todos los elementos de la lista.
>>> lista.clear()
>>> print(lista)
[]     


Podemos conseguir lo mismo también con las siguientes instrucciones:

>>> lista=[2, 5, 2, 6, 7, 2]
>>> # Vaciamos todos los elementos de la lista.
>>> lista=[]
>>> print(lista)
[]
# O también podemos vaciarla entera o solo una parte usando
# del y usando slicing de listas.
>>> lista=[2, 5, 2, 6, 7, 2]
>>> del lista[:]
>>> print(lista)
[]


*)     nombre_lista.reverse()        Devuelve la misma lista pero al revés.

>>> lista=[2, 5, 2, 6, 7, 2]
>>> lista.reverse()
>>> print(lista)
[2, 7, 6, 2, 5, 2]
# lo mismo lo podríamos conseguir con lista[::-1]


*)     nombre_lista.sort()            Ordena solamente los elementos de una lista. Por defecto modifica la lista orignal y lo hace en orden creciente, a no ser que como argumento usemos reverse=True que lo haría en orden decreciente.

>>> lista=[2, 5, 2, 6, 7, 2]
>>> lista.sort() # Orden creciente
>>> print(lista)
[2, 2, 2, 5, 6, 7]
>>> lista.sort(reverse=True) # Orden decreciente
[7, 6, 5, 2, 2, 2]


Opcionalmente también podríamos usar la función sorted(), que no solo puede ordenar listas sino cualquier otro iterable. Además sorted() no modifica la lista original, sino que devuelve la lista ordenada. 

>>> lista=[2, 5, 2, 6, 7, 2]
>>> x = sorted(lista)
>>> print(x)
[2, 2, 2, 5, 6, 7]
>>> print(lista)
[2, 5, 2, 6, 7, 2]


*)     nombre_lista.copy()         Devuelve una copia de esa lista. Si simplemente asignamos una lista a una variable no estamos copiando la lista en otra independiente sino solo haciendo una referencia a la misma. Por tanto si lo que queremos es copiar una lista tenemos que hacer uso del método .copy()

>>> lista=[2, 5, 2, 6, 7, 2]
>>> x = lista # Esto no copia la lista en una independiente, solo hacemos una referencia
a la misma.
>>> x.append(9)
>>> print(lista)
[2, 5, 2, 6, 7, 2, 9]
>>> z = lista.copy() # Crea una verdadera copia independiente de la lista.
>>> print(z)
[2, 5, 2, 6, 7, 2, 9]


Otras funciones y otras cosas que se pueden aplicar a una lista.


*)     sum(lista)            Devuelve la suma de los elementos de la lista.

>>> lista = [2, 5, 2, 6, 7, 2, 9]
>>> print(sum(lista)) 
33


*)     max(lista)            Devuelve el valor máximo de una lista.

>>> lista = [2, 5, 2, 6, 7, 2, 9]
>>> print(max(lista)) 
9


*)    min(lista)            Devuelve el valor mínimo de una lista.

>>> lista = [2, 5, 2, 6, 7, 2, 9]
>>> print(min(lista)) 
2


Cuando estamos asignando elementos de un iterable a unas variables, si a una de estas variables le anteponemos un *, Python se encarga de asignarle todos los valores del iterable que le dejen la asignación de las otras variables.

>>> lista = [2, 5, 2, 6, 7, 2, 9]
>>> a, *b, c = lista
>>> print(a)
2
>>> print(b)
[5, 2, 6, 7, 2]
>>> print(c)
9


*) Operador especial "in" aplicado a una lista.         Nos dice si un determinado elemento esta en la lista.

Devuelve True si el elemento esta en la lista y False en caso contrario.

>>> lista = ['angel','andres','maria']
>>> print('maria' in lista)
True


Compresión de listas (list comprehensions).

Nos sirve para crear una nueva lista, excluyendo o trasformando sus elementos, pero de una forma más rápida y que se lea mejor que utilizando el código normal y en una sola línea de código.  

Toda compresión de listas puede ser representada con un bucle for, pero no todo bucle for, puede ser representado como una compresión de listas.

La síntesis de una compresión de listas es la siguiente:

[expression for item in lista condicional]

Esto se puede usar con cualquier iterable, no solo con las listas.

Lo mejor es verlo con ejemplos:

Vamos a obtener una nueva lista, de una lista que ya tenemos, con los números que sean mayores que 10.

>>> lista = [4,22,58,4,1,20,8]
>>> lista_nueva = [x for x in lista if x>10]
>>> print(lista_nueva)
[22, 58, 20]

Esto mismo se podría haber hecho de forma, digamos tradicional usando el siguiente código:

>>> lista = [4,22,58,4,1,20,8]
>>> lista_nueva = []
>>> for x in lista:
>>>   if x > 10:
>>>    lista_nueva.append(x)
print(lista_nueva)
[22, 58, 20]


Otro ejemplo. Multiplicar por 2 los elementos de una lista.

>>> lista = [4,22,58,4,1,20,8]
>>> lista_nueva = [x * 2 for x in lista]
>>> print(lista_nueva)
[8, 44, 116, 8, 2, 40, 16]

 

O por ejemplo también podemos usar  bucles anidados para ciertas cosas, por ejemplo crear puntos de coordenadas:

>>> points = [(x, y) for y in range(0, 3) for x in range(0, 5)]
>>> print(points)
[(0, 0), (1, 0), (2, 0), (3, 0), (4, 0), 
 (0, 1), (1, 1), (2, 1), (3, 1), (4, 1), 
 (0, 2), (1, 2), (2, 2), (3, 2), (4, 2)]
que de forma tradicional llevarían más trabajo:

  1. points = []
  2. for y in range(0, 3):
  3. for x in range(0, 5):
  4. points.append((x, y))
  5. print(points)

e incluso podríamos haber utilizado una condición para mostrar solo los puntos en los que x == y.

  1. points = [(x, y) for x in range(0, 5) for y in range(0, 5)
  2. if x == y]
Para finalizar, si alguna vez necesitamos evaluar una lista, es útil usar los comandos ALL y ANY. (todos o alguno en español)

Por ejemplo si tenemos una serie de números en una lista y queremos saber si son mayores que uno dado podemos usar lo siguiente para abreviar código.

> numeros = [55, 44, 33, 22, 7]
> # ¿Son todos mayores que 5?
> if all([i>5 for i in numeros]):
>	print("Todos los números son mayores que 5.")
Todos los números son mayores que 5.

O si tenemos una lista de números y queremos saber si alguno de ellos es par podemos usar:

> numeros = [55, 44, 33, 22, 7]
> # ¿Alguno de ellos es par?
> if any([i%2==0 for i in numeros]):
     print("al menos un número es par")
> else:
     print("ninguno es par")    

Puedes encontrar más información sobre listas, tuplas y secuencias en la documentación oficial.

sábado, 20 de marzo de 2021

Condicionales en Python



Los condicionales son sentencias de código que solo se ejecutarán si se cumple la condición establecida (operadores lógicos).

Por ejemplo, si tenemos un número almacenado en la variable x, podemos hacer el siguiente condicional:

1 x = 30

2 if  x < 20:

3     print(f"{x} es menor que 20")

4 elif x < 25:

    print(f'{x} es mayor que 20 pero menor que 25')

6 else:

    print(f"{x} es mayor que 25")


En este ejemplo el valor almacenado en la variable x es 30. El programa lee la instrucción de la línea 2 if (si) que se podría traducir como si x es menor que 20 entonces ejecuta el código que está indentado en la linea 3. Como esto no es verdad, no se ejecuta el código y se pasa a la siguiente línea, a la instrucción elif.

La palabra clave elif (de lo contrario Si) es la forma que tiene Python de decir "Si las condiciones anteriores no son verdaderas entonces prueba esta condición". En el ejemplo como x no es menor que 25 la condición es falsa, no se ejecuta el código identado y se pasa a la siguiente instrucción.

La instrucción final es else (de lo contrario), que captura cualquier cosa que no sea detectada por las condiciones anteriores, es decir que si todo lo anterior no se cumple (else = Si no) se ejecute el código identado en la línea 7.


Cuando utilizamos un condicional sin más (if Expresión:) sin poner ninguna condición, lo que se quiere decir en realidad es que si algo es True se ejecute el código de la condición. Por ejemplo:

>>> x = 30
>>> if x:
>>>     print("x es True")
True        

La expresión de la sentencia if se evalúa a False cuando en la expresión a evaluar se dan alguna de las siguientes circunstancias:

- Cualquier número igual a cero.

- Cualquier contenedor que este vacío. (lista, tupla, conjunto, diccionario)

- La expresión False o None.


Otros operadores que podemos usar son:


Operadores de identidad en Python.

Se usan para comparar los objetos, no si son iguales,  sino si en realidad son el mismo objeto, con la misma ubicación en memoria.

Operador is:

Significa una prueba de identidad, ambos lados de la expresión condicional deben ser el mismo objeto.

a = 1
b = 1
if a is b:
  print("a es idéntico que b")

SALIDA:
a es idéntico que b 

Operador is not:

Devuelve True si ambas variables no son el mismo objeto.

x = ["manzana", "plátano"]
y = ["manzana", "plátano"]
z = x

print(x is not z)

# devuelve False porque z es el mismo objeto que x

print(x is not y)

# devuelve True porque x no es el mismo objeto que y, aunque ambas tengan el mismo contenido.

print(x != y)

# para que veas la diferencia entre "is not" and "!=": Esta comparación devuelve False 
# porque x tiene el mismo contenido que y


Operadores de pertenencia en Python:

Operador in:

El operador in, significa, que para cualquier colección (lista, tupla etc) el elemento del lado izquierdo está en el lado derecho del operador.

b = [1,2,3]
if 2 in b:
   print("2 esta en la lista b")

SALIDA:
2 esta en la lista b

Operador not in:

Es el contrario del anterior, y devuelve True cuando el elemento no esta en una secuencia de datos.

b = [1,2,3]
if 5 not in b:
  print("5 no esta en la lista b")
else: 
  print("5 está en la lista b")

SALIDA:
5 no esta en la lista b


El operador not (lo contrario) devuelve True si las declaraciones no son verdaderas y False si lo son.

x = 5

print(not(x > 3 and x < 10))

SALIDA:
False
# devuelve False porque not se utiliza para dar la vuelta al resultado.


También se pueden unir varias condiciones usando los operadores lógicos:


and  (Traducido como "y")

a = 200
b = 33
c = 500
if a > b and c > a:
  print("Todas las condiciones son verdaderas")

Salida:
Todas las condiciones son verdaderas


Or (Traducido como "o")

a = 200
b = 33
c = 500
if a > b or a > c:
  print("Al menos una de las condiciones es verdadera")

Salida:
Al menos una de las condiciones es verdadera


Podemos asignar un valor a una variable de forma abreviada usando una condición es lo que se conoce como Ternary Operator u Operador Ternario ( de 3 elementos: variable, valor True y valor False). Si la condición es cierta se le asignará un valor a la variable y si es Falsa otro distinto. 

a = 7
b = 5 if a > 6 else 2
print(b)

Salida:
5
# La variable valdría 2 si la variable a no fuera mayor que 6


Los operadores de comparación que se pueden utilizar tanto en condicionales como en bucles son:

Igual: a==b
No igual: a!=b
Menor que: a < b
Menor que o igual que: a <= b
Más grande que: a > b
Más grande o igual que: a >= b


Puedes encontrar más información sobre operadores de Python en esta página de w3schools.


Uso de la declaración Switch de otros lenguajes en Python.


Hasta la versión 3.10, Python nunca tuvo una función que implementara lo que hace la instrucción switch en otros lenguajes de programación.

Entonces, si querías ejecutar varias declaraciones condicionales, tendrías que usar la palabra clave elif de esta manera:

edad = 120

if edad > 90:
    print("Ya tienes una edad considerable.")
elif edad < 0:
    print("Aun no has ni nacido")
elif edad >= 18:
    print("¿Ya puedes ir de fiesta?")
else: 
    print("Aun te queda mucho por delante.")

# Salida: Ya tienes una edad considerable.

Desde la versión 3.10 en adelante, Python ha implementado esta característica con las palabras clave "match" y "case

Para escribir declaraciones de este tipo se puede seguir la siguiente estructura:

match término:
    case patrón-1:
         acción-1
    case patrón-2:
         acción-2
    case patron-3:
         acción-3
    case _:
        acción_por_defecto

Ten en cuenta que el símbolo de subrayado es lo que se usa para definir un caso por defecto en Python.

A continuación vamos a ver un ejemplo con esta nueva funcionalidad.

vocal = input("Introduzca una vocal: ")

match vocal:
    case 'a':
        print("la vocal es la a")
    case 'e':
        print("la vocal es la e")
    case 'i':
        print("la vocal es la i")
    case 'o':
        print("la vocal es la o")
    case _:
        print("la vocal es la u u otra cosa")