Si estoy clasificando una secuencia usando el paradigma funcional, ¿no es un desperdicio hacer copias?

Objetivo: ordenar una secuencia de una manera funcional sin usar el comando incorporado sorted(..) función.

def my_sorted(seq):
    """returns an iterator"""
    pass

Motivación: En el modo FP, estoy limitado:

  • nunca mutes seq (que podría ser un iterador o una lista realizada)
  • Por implicación, no hay clasificación en el lugar.

Pregunta 1 Como no puedo mutar seq, necesitaría mantener una estructura de datos mutable separada para almacenar la secuencia ordenada. Eso parece un desperdicio en comparación con un lugar list.sort(). ¿Cómo manejan esto otros lenguajes de programación funcional?

Pregunta 2 Si devuelvo una secuencia mutable, ¿está bien en el paradigma funcional?

preguntado el 22 de mayo de 12 a las 11:05

5 Respuestas

Por supuesto, la ordenación no puede ser totalmente perezosa (el último elemento de entrada podría ser el primero en la salida), pero podría implementar una ordenación perezosa computacional que, después de leer la secuencia completa, solo genere una salida ordenada exacta a pedido elemento por elemento. También puede retrasar la lectura de la entrada hasta que se solicite al menos una salida, por lo que ordenar e ignorar el resultado no requerirá ningún cálculo.

Para este enfoque computacionalmente perezoso, el mejor candidato que conozco es el algoritmo heapsort (solo realiza el paso de creación de montón por adelantado).

contestado el 22 de mayo de 12 a las 11:05

La mutación en el lugar solo es segura si nadie más tiene referencias a los datos, esperando que sean como eran antes de la clasificación. Por lo tanto, no es un desperdicio tener una nueva estructura para los resultados ordenados, en general. La optimización en el lugar solo es segura si está utilizando los datos en un lineal la moda.

Entonces, simplemente asigne una nueva estructura, ya que eso es más útil en general. La versión in situ es un caso especial.

contestado el 22 de mayo de 12 a las 13:05

La programación defensiva adecuada is a veces es un desperdicio, pero tampoco hay nada que puedas hacer al respecto.

Esta es la razón por la que los lenguajes creados para admitir el uso funcional desde cero utilizan el intercambio estructural para sus tipos inmutables de forma nativa; la programación en un estilo funcional en un lenguaje que no está diseñado para él (como Python) no será tan compatible como una cuestión de rutina. Dicho esto, una operación de ordenación no es necesariamente una buena candidata para el uso compartido estructural (si es necesario realizar más que cambios menores).

Como tal, a menudo is al menos una operación de copia involucrada en una clasificación, incluso en otros lenguajes funcionales. Clojure, por ejemplo, delega a la operación de clasificación nativa (altamente optimizada) de Java en una matriz mutable temporal y devuelve una secuencia que envuelve esa matriz (y, por lo tanto, hace que el resultado sea tan inmutable como la entrada que se usó para completar la misma). Si las entradas son inmutables y las salidas son inmutables, y lo que sucede en el medio no es visible para el mundo exterior (particularmente, para cualquier otro subproceso), la mutabilidad transitoria es a menudo algo necesario y apropiado.

contestado el 22 de mayo de 12 a las 14:05

Utilice un algoritmo de clasificación que se pueda realizar de manera que cree una nueva estructura de datos, como heapsort o mergesort.

contestado el 22 de mayo de 12 a las 11:05

¿Despilfarro de qué? pedacitos? ¿electricidad? hora del reloj de pared? Un merge-sort paralelo puede ser el más rápido de completar si tiene suficiente CPU y una gran cantidad de datos, pero puede producir muchas representaciones intermedias.

En general, paralelizar un algoritmo puede conducir a una estrategia de optimización muy diferente a la de un algoritmo en serie. Por ejemplo, debido a la Ley de Amdahl, volver a realizar el trabajo redundante localmente para evitar compartir. Esto puede considerarse "despilfarro" en un contexto serial, pero conduce a un algoritmo mucho más escalable.

contestado el 23 de mayo de 12 a las 22:05

No es la respuesta que estás buscando? Examinar otras preguntas etiquetadas or haz tu propia pregunta.