Listas y Tuplas en Python

Listas en Python

Las listas en Python son colecciones ordenadas y mutables de elementos. Pueden contener cualquier tipo de dato, como números, cadenas, booleanos, u otros objetos de Python.

Creación y Acceso a Listas

A continuación se presentan ejemplos de creación y acceso a listas:

  1. Ejemplo de una lista de números enteros:

     1a = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
     2print(a[0])      # 1
     3print(a[-1])     # 10
     4print(a[:5])     # [1, 2, 3, 4, 5]
     5print(a[3:4])    # [4]
     6print(a[::-1])   # [10, 9, 8, 7, 6, 5, 4, 3, 2, 1]
     7print(a[::2])    # [1, 3, 5, 7, 9]
     8print(a[1::2])   # [2, 4, 6, 8, 10]
     9print(a[2:7:2])  # [3, 5, 7]
    10print(a[::-2])   # [10, 8, 6, 4, 2]
    11print(a[7:1:-3])  # [8, 5]
    
    • a[0] accede al primer elemento de la lista “a” (índice 0) y lo imprime.

    • a[-1] accede al último elemento de la lista “a” (índice -1) y lo imprime.

    • a[:5] devuelve una sublista de “a” que contiene los primeros 5 elementos y la imprime.

    • a[3:4] devuelve una sublista de “a” que contiene el elemento en el índice 3 y lo imprime.

    • a[::-1] devuelve una sublista de “a” en orden inverso y la imprime.

    • a[::2] devuelve una sublista de “a” que contiene elementos con un paso de 2, comenzando desde el principio.

    • a[1::2] devuelve una sublista de “a” que contiene elementos con un paso de 2, comenzando desde el segundo elemento.

    • a[2:7:2] devuelve una sublista de “a” que contiene elementos con un paso de 2, comenzando desde el tercer elemento y hasta el séptimo (sin incluirlo).

    • a[::-2] devuelve una sublista de “a” en orden inverso con un paso de 2.

    • a[7:1:-3] devuelve una sublista de “a” que contiene elementos con un paso de -3, comenzando desde el índice 7 y retrocediendo hasta el índice 1 (sin incluirlo).

    La notación usada cuando se saca una sublista de la lista se conoce como slicing. En esta, se especifica el elemento inicial de la sublista, el elemento final de la sublista y el incremento. El incremento puede ser positivo o negativo.

  2. Ejemplo con la lista con elementos de diferente tipo (números enteros y cadenas de caracteres).

    1 b = [1, 'dos', 3, 'cuatro']
    2 print(b)      # [1, 'dos', 3, 'cuatro']
    3 print(b[1])   # 'dos'
    

El Bucle for en Python

El bucle for en Python se utiliza para iterar sobre una secuencia de elementos, como una lista, tupla, cadena o cualquier objeto iterable. Se utiliza comúnmente para realizar operaciones repetitivas en una secuencia de elementos.

Por ejemplo, podríamos utilizar un bucle for para imprimir cada elemento de una lista:

1 lista = [1, 2, 3, 4, 5]
2 for elemento in lista:
3     print(elemento)

Este bucle imprimirá cada elemento de la lista en una línea separada.

Usando lista de listas como una lista multidimensional

Las listas en Python pueden contener elementos de cualquier tipo, incluso otras listas. Esto permite representar estructuras de datos multidimensionales de forma sencilla. Por ejemplo, la siguiente lista c contiene tres listas internas, cada una con dos elementos:

1c = [[4, 5], [2, 3], [8, 9]]
2print(c)
3# Salida: [[4, 5], [2, 3], [8, 9]]
4
5print(c[0])
6# Salida: [4, 5]
7
8print(c[1][1])
9# Salida: 3

Esto permite acceder a elementos específicos dentro de la lista principal y de las listas internas mediante la indexación, simulando una matriz de datos.

Operaciones aritméticas entre listas

Python permite realizar operaciones aritméticas entre listas. Por ejemplo, la siguiente operación multiplica una lista por un escalar:

1d = 10 * [1]
2print(d)
3# Salida: [1, 1, 1, 1, 1, 1, 1, 1, 1, 1]

También es posible concatenar varias listas mediante el operador +:

1a = [1, 2, 3] + [4, 5, 6] + [7]
2print(a)
3# Salida: [1, 2, 3, 4, 5, 6, 7]

Modificando listas

Las listas en Python son mutables, lo que significa que sus elementos pueden ser modificados después de su creación.

Modificando un elemento de la lista

Para modificar un elemento específico de una lista, se puede acceder a dicho elemento mediante su índice y asignarle un nuevo valor:

1a = [1, 2, 3]
2
3a = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
4a[4] = 'cinco'
5print(a)
6# Salida: [1, 2, 3, 4, 'cinco', 6, 7, 8, 9, 10]

Modificando varios elementos de la lista

Para modificar varios elementos consecutivos de una lista, se puede asignar una lista de valores a un rango de índices:

1a = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
2a[2:5] = ['tres', 'cuatro', 'cinco']
3print(a)
4# Salida: [1, 2, 'tres', 'cuatro', 'cinco', 6, 7, 8, 9, 10]

También es posible modificar elementos utilizando un paso diferente de 1:

1a[::2] = ['*', '*', '*', '*', '*' ]
2print(a)
3# Salida: ['*', 2, '*', 4, '*', 6, '*', 8, '*', 10]

En este caso, es importante que las dos listas, tanto la de la izquierda a la que se le está asignando como la de la derecha, tengan el mismo número de elementos.

Adicionando elementos al final de la lista

Para añadir elementos al final de una lista, podemos utilizar el método append:

1a = [1, 2, 3, 4, 5]
2a.append(6)
3a.append(7)
4print(a)
5# Salida: [1, 2, 3, 4, 5, 6, 7]

Extendiendo la lista

El método extend permite agregar múltiples elementos al final de una lista, modificando la lista original. A diferencia del operador +, que concatena listas creando una nueva lista, el método extend es más eficiente en términos de uso de memoria ya que no crea una nueva lista.

 1# Uso de extend
 2a = [1, 2, 3]
 3a.extend([4, 5, 6])
 4print(a)
 5# Salida: [1, 2, 3, 4, 5, 6]
 6
 7# Uso del operador +
 8b = [1, 2, 3]
 9c = b + [4, 5, 6]
10print(c)
11# Salida: [1, 2, 3, 4, 5, 6]
12
13# Nota importante
14print(b)
15# Salida: [1, 2, 3]

En el caso del método extend, la lista a se modifica directamente con los nuevos elementos, mientras que cuando utilizamos el operador +, se crea una nueva lista c que es la concatenación de b y los nuevos elementos. La lista original b permanece sin cambios.

Eliminando elementos de la lista

Para eliminar elementos de una lista, podemos utilizar la sintaxis de rebanado (del) o el método remove:

1a = [1, 2, 3, 4, 5]
2del a[2:4]
3print(a)
4# Salida: [1, 2, 5]
5
6b = [1, 2, 3, 4, 5]
7b.remove(3)
8print(b)
9# Salida: [1, 2, 4, 5]

Copiando listas

La asignación de una lista a otra variable simplemente crea una referencia, no una copia independiente. Esto significa que ambas variables apuntan a la misma ubicación de memoria y cualquier cambio realizado en una lista también afectará a la otra.

1a = [1, 2, 3, 4]
2b = a  # Asignación de referencia, no de copia
3a[0] = 0
4
5print(a)
6# Salida: [0, 2, 3, 4]
7
8print(b)
9# Salida: [0, 2, 3, 4]

En este caso, tanto la lista a como la lista b están apuntando a la misma ubicación de memoria, por lo que cualquier cambio realizado en una de las listas se reflejará en la otra.

Para crear una copia de una lista, podemos utilizar la técnica de rebanado o el método copy:

Técnica del rebanado

La técnica de rebanado consiste en crear una nueva lista que contiene todos los elementos de la lista original. Esto se logra utilizando la notación de rebanado con dos puntos, lo que crea una copia independiente de la lista original.

1a = [1, 2, 3, 4]
2b = a[:]  # Creamos una copia de la lista a
3a[0] = 0
4
5print(a)
6# Salida: [0, 2, 3, 4]
7
8print(b)
9# Salida: [1, 2, 3, 4]

En este caso, la lista b es una copia independiente de la lista a, por lo que cualquier modificación realizada en a no afectará a b.

Método copy

El método copy también crea una copia de la lista original. Esta copia contiene los mismos elementos que la lista original.

1a = [1, 2, 3, 4]
2b = a.copy()  # Otra forma de crear una copia de la lista a
3a[0] = 0
4
5print(a)
6# Salida: [0, 2, 3, 4]
7
8print(b)
9# Salida: [1, 2, 3, 4]

En este caso, la lista b es una copia independiente de la lista a. Sin embargo, si los elementos de la lista fueran objetos mutables y se modificaran dentro de a, esos cambios también se reflejarían en b.

Advertencia

Estas dos formas de copia realizan copias superficiales, lo que significa que lo que se copian son referencias a los objetos que están almacenados en la lista. Por lo tanto, si los elementos de la lista son objetos mutables (como una lista), los cambios en esos objetos afectarán a ambas listas, pues ambas listas hacen referencia al mismo objeto.

1a = [1, [2, 3], 3, 4]
2b = a.copy()
3
4a[1].append(4)
5
6print(a)  # Salida: [1, [2, 3, 4], 3, 4]
7print(b)  # Salida: [1, [2, 3, 4], 3, 4]

Métodos importantes de las listas

A continuación se presentan algunos métodos importantes de las listas. La documentación completa de los métodos de las listas se puede encontrar en: https://docs.python.org/3/tutorial/datastructures.html#more-on-lists

Buscando información de la lista

Para buscar información específica en una lista, Python proporciona dos métodos: count e index:

1l = [1, 2, 3, 4, 5, 6, 7, 8, 9, 1, 2, 3, 4, 5, 6, 7, 8, 9]
2
3print(l.count(4))
4# Salida: 2
5# ¿Cuantos cuatros hay?
6
7print(l.index(4))
8# Salida: 3
9# ¿Donde esta el primer 4?

Otra forma de agregar información a una lista

El método insert permite agregar un elemento en una posición específica de una lista:

1l = [1, 2, 3, 5, 6, 7, 8, 9]
2l.insert(3, 4)  # Insertamos '4' en la posición 3
3print(l)
4# Salida: [1, 2, 3, 4, 5, 6, 7, 8, 9]

Sacando elementos de una lista

Para retirar elementos de una lista, Python proporciona el método pop, que elimina y devuelve el último elemento por defecto, o un elemento específico si se especifica un índice:

 1l = [1, 2, 3, 4, 5]
 2print(l.pop())
 3# Salida: 5
 4# Retornamos y removemos el ultimo item de la lista
 5
 6print(l.pop(3))
 7# Salida: 4
 8# Retornamos y removemos el cuarto item de la lista
 9
10l.remove(3)
11# Removemos el primer 3 que se encuentre en la lista

Formas fáciles de cambiar el orden de una lista

Los métodos reverse y sort permiten cambiar el orden de una lista:

1l = [3, 2, 5, 1, 4]
2l.reverse()  # Invertimos la lista
3print(l)
4# Salida: [4, 1, 5, 2, 3]
5
6l.sort()  # Ordenamos la lista
7print(l)
8# Salida: [1, 2, 3, 4, 5]

La función range

La función range(start, stop, step) genera una secuencia de enteros comenzando desde start (inclusive) y terminando antes de stop (exclusivo), con un intervalo definido por step. Por defecto, start se establece en 0 y step en 1, lo que crea una secuencia de números consecutivos desde 0 hasta uno menos que stop.

Aunque range en Python 3 no genera una lista directamente, sino un objeto iterable de tipo range, se puede convertir fácilmente a una lista si se desea.

Ejemplo de uso:

1# Genera una secuencia desde 0 hasta 4
2for i in range(5):
3    print(i)
4# Salida: 0 1 2 3 4
5
6# Genera una secuencia desde 2 hasta 9 con un paso de 2
7numeros = list(range(2, 10, 2))
8print(numeros)
9# Salida: [2, 4, 6, 8]

En el primer ejemplo, range(5) genera una secuencia de números desde 0 hasta 4. En el segundo ejemplo, range(2, 10, 2) genera números pares desde 2 hasta 8.

Algunas funciones que operan sobre las listas

Python proporciona algunas funciones integradas útiles para operar sobre listas:

 1l = [0, 3, 5, 1]
 2l1 = [0, 3, 4, 1]
 3print(cmp(l, l1))  # Retorna 0 si las listas son iguales
 4# Salida: 0
 5print(len(l)) # Retorna el número de elementos de la lista
 6# Salida: 4
 7print(max(l)) # Retorna el valor del elemento mas grande de la lista
 8# Salida: 5
 9print(min(l)) # Retorna el valor del elemento mas pequeño de la lista
10# Salida: 0

Tuplas

Las tuplas son estructuras de datos en Python similares a las listas, pero con la diferencia principal de que son inmutables, es decir, una vez creadas no pueden modificarse. Son útiles para almacenar colecciones de elementos que no necesitan cambios.

Creando tuplas

Para crear una tupla, simplemente separen los elementos con comas y, opcionalmente, pueden usar paréntesis para mayor claridad.

1a = (1, 2, 3)
2b = 34, 56, 'ww'
3print(a)  # Salida: (1, 2, 3)
4print(a[2])  # Salida: 3

Diferencia entre listas y tuplas

Las principales diferencias entre las listas y las tuplas son:

  • Las tuplas son inmutables, lo que significa que no se pueden modificar después de haber sido creadas.

  • Los métodos de las listas, como append() o extend(), no funcionan en las tuplas porque estas no admiten modificaciones después de la creación.

Similitudes entre listas y tuplas

A pesar de sus diferencias, las tuplas y las listas comparten varias similitudes:

  • El indexado en las tuplas funciona de la misma manera que en las listas, utilizando corchetes para acceder a elementos específicos.

  • Las funciones y métodos que trabajan con listas, como len(), max(), min() y sum(), también se pueden utilizar con tuplas.

Otras características de las tuplas

Además de las diferencias y similitudes mencionadas, aquí hay algunas otras características y consideraciones importantes sobre las tuplas en Python:

  1. Eficiencia: - Las tuplas son más eficientes en cuanto a memoria y rendimiento que las listas, ya que son estructuras de datos inmutables y ocupan menos espacio en la memoria.

    Ejemplo:

    1lista = [1, 2, 3, 4, 5]
    2tupla = (1, 2, 3, 4, 5)
    3
    4print("Tamaño de la lista:", sys.getsizeof(lista))
    5print("Tamaño de la tupla:", sys.getsizeof(tupla))
    
  2. Iterabilidad: - Al igual que las listas, las tuplas son iterables, lo que significa que se pueden recorrer fácilmente utilizando bucles for.

    Ejemplo:

    1tupla = (1, 2, 3, 4, 5)
    2
    3for elemento in tupla:
    4    print(elemento)
    
  3. Asignación de desempaquetado: - Las tuplas permiten la asignación de desempaquetado, lo que significa que pueden desempaquetarse en variables individuales con una sola instrucción de asignación.

    Ejemplo:

    1tupla = (1, 2, 3)
    2a, b, c = tupla
    3
    4print("a:", a)
    5print("b:", b)
    6print("c:", c)
    
  4. Uso en funciones: - Las tuplas se utilizan frecuentemente en Python para devolver múltiples valores desde una función.

    Ejemplo:

    1def calcular_resultados(numero):
    2    cuadrado = numero ** 2
    3    cubo = numero ** 3
    4    return cuadrado, cubo
    5
    6resultado_cuadrado, resultado_cubo = calcular_resultados(3)
    7print("Cuadrado:", resultado_cuadrado)
    8print("Cubo:", resultado_cubo)
    
  5. Uso en estructuras de datos más complejas: - Las tuplas se pueden utilizar como elementos en otras estructuras de datos más complejas, como diccionarios o listas de tuplas.

    Ejemplo:

    1tabla = [
    2    ('Juan', 25),
    3    ('María', 30),
    4    ('Pedro', 28)
    5]
    6
    7for nombre, edad in tabla:
    8    print(f"{nombre} tiene {edad} años.")
    
  6. Inmutabilidad y seguridad: - La inmutabilidad de las tuplas proporciona seguridad de datos, ya que garantiza que los elementos de la tupla no se modifiquen accidentalmente una vez creados.

Tarea

  • Buscar que son lo diccionarios (dictionaries) y los conjuntos (sets) en Python.

Ejercicios

La idea de los siguientes ejercicios es promover el pensamiento lógico de programación, por lo tanto, no se pueden usar las funciones de Python como max, min, sum o similares, ni librerías como numpy o parecidas. Tampoco métodos como sort, reverse, etc.

  1. Suma de elementos: Escriba un código que tome una lista de números como entrada y calcule la suma de todos los elementos de la lista.

  2. Producto de elementos pares: Escriba un código que tome una lista de números como entrada y calcule el producto de todos los elementos pares de la lista.

  3. Promedio de elementos: Escriba un código que tome una lista de números como entrada y calcule el promedio de todos los elementos de la lista.

  4. Mayor elemento: Escriba un código que tome una lista de números como entrada y encuentre el mayor elemento de la lista.

  5. Ordenar lista: Escriba un código que tome una lista de números como entrada y genere una nueva lista con los elementos ordenados de forma ascendente.

  6. Eliminar duplicados: Escriba un código que tome una lista de números como entrada y genere una nueva lista con los elementos únicos de la lista original, sin duplicados.

  7. Invertir lista: Escriba un código que tome una lista de números como entrada y genere una nueva lista con los elementos en orden inverso al de la lista original.

  8. Contar elementos pares e impares: Escriba un código que tome una lista de números como entrada y cuente la cantidad de elementos pares y la cantidad de elementos impares en la lista.

  9. Media móvil: Escriba un código que tome una lista de números como entrada y un entero k, y calcule una nueva lista donde cada elemento sea la media móvil de los k elementos anteriores en la lista original.

  10. Multiplicación de matrices: Escriba un código que tome dos listas de listas (matrices) como entrada y calcule el resultado de multiplicar las dos matrices.