Orden de Python

La forma más fácil de ordenar es con la función order(list), que toma una lista y devuelve una lista nueva con esos elementos en orden. La lista original no se modifica.

  a = [5, 1, 4, 3]
  print(sorted(a))  ## [1, 3, 4, 5]
  print(a)  ## [5, 1, 4, 3]

Es más común pasar una lista a la función order(), pero, de hecho, puede tomar como entrada cualquier tipo de colección iterable. El método list.sort() anterior es una alternativa que se detalla a continuación. La función order() parece ser más fácil de usar en comparación con sort(), por lo que te recomiendo usar esta función.

La función order() se puede personalizar usando argumentos opcionales. El argumento opcional order() inverso=True, p.ej., ordenado(lista, inverso=verdadero), hace que ordene de forma inversa.

  strs = ['aa', 'BB', 'zz', 'CC']
  print(sorted(strs))  ## ['BB', 'CC', 'aa', 'zz'] (case sensitive)
  print(sorted(strs, reverse=True))   ## ['zz', 'aa', 'CC', 'BB']

Ordenación personalizada con key=

Para un orden personalizado más complejo, order() toma una "key=" especificar una "clave" que transforma cada elemento antes de la comparación. La función clave toma 1 valor y devuelve 1 valor, además del “proxy” que se devuelve. value se usa para las comparaciones dentro del orden.

Por ejemplo, con una lista de cadenas, especificando key=len (la función integrada len()) las cadenas se ordenan por longitud, de la más corta a la más larga. El ordenamiento llama a len() para cada string a fin de obtener la lista de valores de longitud proxy y, luego, ordena con esos valores.

  strs = ['ccc', 'aaaa', 'd', 'bb']
  print(sorted(strs, key=len))  ## ['d', 'bb', 'ccc', 'aaaa']

la llamada se ordenó con key=len

Como otro ejemplo, si especificas "str.lower" ya que la función clave es una forma de forzar el ordenamiento de modo que se traten las mayúsculas y minúsculas de la misma manera:

  ## "key" argument specifying str.lower function to use for sorting
  print(sorted(strs, key=str.lower))  ## ['aa', 'BB', 'CC', 'zz']

También puedes pasar tu propia función MyFn como la función clave, de la siguiente manera:

  ## Say we have a list of strings we want to sort by the last letter of the string.
  strs = ['xc', 'zb', 'yd' ,'wa']

  ## Write a little function that takes a string, and returns its last letter.
  ## This will be the key function (takes in 1 value, returns 1 value).
  def MyFn(s):
    return s[-1]

  ## Now pass key=MyFn to sorted() to sort by the last letter:
  print(sorted(strs, key=MyFn))  ## ['wa', 'zb', 'xc', 'yd']

Para una ordenación más compleja, como ordenar por apellido y, luego, por nombre, Puedes usar las funciones itemgetter o attrgetter, como las siguientes:

  from operator import itemgetter

  # (first name, last name, score) tuples
  grade = [('Freddy', 'Frank', 3), ('Anil', 'Frank', 100), ('Anil', 'Wang', 24)]
  sorted(grade, key=itemgetter(1,0))
  # [('Anil', 'Frank', 100), ('Freddy', 'Frank', 3), ('Anil', 'Wang', 24)]

  sorted(grade, key=itemgetter(0,-1))
  #[('Anil', 'Wang', 24), ('Anil', 'Frank', 100), ('Freddy', 'Frank', 3)]

Método sort()

Como alternativa a order(), el método sort() en una lista ordena esa lista en orden ascendente, p.ej., list.sort(). El método sort() cambia la lista subyacente y muestra None, así que úsalo de la siguiente manera:

  alist.sort()            ## correct
  alist = blist.sort()    ## Incorrect. sort() returns None

Lo anterior es un malentendido muy común sobre sort(), ya que *no muestra* la lista ordenada. El método sort() debe llamarse en una lista; no funciona en ninguna colección que se pueda enumerar (pero la función order() anterior funciona en cualquier cosa). El método sort() es anterior a la función order(), por lo que es probable que la veas en códigos anteriores. El método sort() no necesita crear una lista nueva, por lo que puede ser un poco más rápido en el caso de que los elementos para ordenar ya estén en una lista.

Tuplas

Una tupla es una agrupación de tamaño fijo de elementos, como una coordinación (x, y). Las tuplas son como las listas, excepto que son inmutables y no cambian de tamaño (las tuplas no son estrictamente inmutables, ya que uno de los elementos contenidos podría ser mutable). Las tuplas tocan una especie de "struct" en Python: una forma conveniente de pasar un pequeño paquete de valores lógicos y fijos. Una función que necesita mostrar varios valores solo puede mostrar una tupla de valores. Por ejemplo, si quisiera tener una lista de coordenadas en 3D, la representación natural de Python sería una lista de tuplas, en la que cada tupla es de tamaño 3 con un grupo (x, y, z).

Para crear una tupla, solo enumera los valores entre paréntesis separados por comas. La columna "empty" es solo un par vacío de paréntesis. Acceder a los elementos en una tupla es como una lista: len(), [ ], for, in, etc. funcionan de la misma manera.

  tuple = (1, 2, 'hi')
  print(len(tuple))  ## 3
  print(tuple[2])    ## hi
  tuple[2] = 'bye'  ## NO, tuples cannot be changed
  tuple = (1, 2, 'bye')  ## this works

Para crear una tupla size-1, el elemento solitario debe estar seguido de una coma.

  tuple = ('hi',)   ## size-1 tuple

El uso de mayúsculas y minúsculas es raro en la sintaxis, pero la coma es necesaria para distinguir la tupla del uso común de poner una expresión entre paréntesis. En algunos casos, puedes omitir el paréntesis y Python verá de las comas que quieres una tupla.

Asignar una tupla a una tupla de tamaño idéntico de nombres de variables asigna todos los valores correspondientes. Si las tuplas no tienen el mismo tamaño, arroja un error. Esta función también está disponible para listas.

  (x, y, z) = (42, 13, "hike")
  print(z)  ## hike
  (err_string, err_code) = Foo()  ## Foo() returns a length-2 tuple

Comprensión de listas (opcional)

La comprensión de listas es una función más avanzada, lo cual es útil en algunos casos, pero no es necesaria para los ejercicios y no es algo que debas aprender al principio (es decir, puedes omitir esta sección). La comprensión de listas es una forma compacta de escribir una expresión que se expande a una lista completa. Supongamos que tenemos una lista de números [1, 2, 3, 4]. Esta es la comprensión de lista para calcular una lista de sus cuadrados [1, 4, 9, 16]:

  nums = [1, 2, 3, 4]

  squares = [ n * n for n in nums ]   ## [1, 4, 9, 16]

La sintaxis es [ expr for var in list ]. for var in list parece un bucle for normal, pero sin los dos puntos (:). La expr a la izquierda se evalúa una vez por cada elemento para proporcionar los valores de la lista nueva. Este es un ejemplo con cadenas, donde cada cadena se cambia a mayúsculas con “!!!” agregado:

  strs = ['hello', 'and', 'goodbye']

  shouting = [ s.upper() + '!!!' for s in strs ]
  ## ['HELLO!!!', 'AND!!!', 'GOODBYE!!!']

Puedes agregar una prueba if a la derecha del bucle for para reducir el resultado. La prueba "if" se evalúa para cada elemento, incluidos solo los elementos en los que la prueba es verdadera.

  ## Select values <= 2
  nums = [2, 8, 1, 6]
  small = [ n for n in nums if n <= 2 ]  ## [2, 1]

  ## Select fruits containing 'a', change to upper case
  fruits = ['apple', 'cherry', 'banana', 'lemon']
  afruits = [ s.upper() for s in fruits if 'a' in s ]
  ## ['APPLE', 'BANANA']

Ejercicio: list1.py

Para practicar el material de esta sección, prueba problemas posteriores en list1.py que usen ordenación y tuplas (en los Ejercicios básicos).