2009-03-22 14 views
7

Me gustaría ajustar la clase PriorityQueue de java en clojure para usar en otra parte de mi programa. Lo que estoy tratando de averiguar es si hay alguna manera de hacer esto de una manera lisa y hacer que la cola de prioridad sea inmutable. ¿Hay alguna buena manera de hacerlo, o voy a estar mejor utilizando PriorityQueue como una estructura de datos mutable?¿Cómo puedo hacer que una clase Java sea inmutable en Clojure?

Respuesta

8

No creo que haya una manera simple de envolver una estructura de datos mutable como una inmutable. Las estructuras de datos inmutables se vuelven eficientes cuando la nueva versión puede compartir datos con la versión anterior de manera inteligente, y realmente no puedo ver cómo se puede hacer sin el acceso a las partes internas de PriorityQueue.

Si realmente quiere una cola de prioridad persistente this thread podría ser interesante. Sin embargo, parece que tienen insertos de tiempo lineal, por lo que si ese es un problema, quizás tenga que buscar otra implementación.

Editar: Pensándolo bien, una implementación simple de una cola de prioridad persistente es solo para almacenar los pares (prio, value) en un conjunto ordenado. Algo como esto:

(defn make-pqueue [] 
    (sorted-set)) 

(defn pqueue-add [pq x prio] 
    (conj pq [prio x])) 

(defn pqueue-peek [pq] 
    (first pq)) 

(defn pqueue-pop [pq] 
    (let [top (first pq)] 
    (disj pq top))) 

Por supuesto, el código anterior es bastante limitado (no hay entradas múltiples, por ejemplo), pero ilustra la idea.

+0

¿Cómo sabe el conjunto ordenado ordenar por prio en el par (prio, valor)? –

+0

Clojure compara vectores lexicográficamente, por lo que primero se ordenará por prioridad, y segundo por valor. – CAdaker

+0

En realidad, mirando la fuente, solo los vectores de igual longitud se comparan lexicográficamente. Pero eso no es un problema en este caso. – CAdaker

7

No se puede convertir automáticamente la clase mutable en inmutable. Uno siempre puede llamar a la clase Java directamente y mutarla.

Para forzar la inmutabilidad, puede implementarlo en clojure o extender la clase java y lanzar excepciones en todas las implementaciones de métodos mutables.

Cuestiones relacionadas