Tenía la impresión de que los seces perezosos siempre se fragmentaban.En Clojure, ¿los seces perezosos siempre se fragmentan?
=> (take 1 (map #(do (print \.) %) (range)))
(................................0)
Como era de esperar 32 puntos se imprimen porque el SEC perezoso devuelto por range
está fragmentada en 32 trozos de elementos. Sin embargo, cuando en lugar de range
Trato esto con mi propia función get-rss-feeds
, la SEC perezoso ya no está fragmentada:
=> (take 1 (map #(do (print \.) %) (get-rss-feeds r)))
(."http://wholehealthsource.blogspot.com/feeds/posts/default")
Sólo un punto se imprime, así que supongo que los perezosos-ss devuelto por get-rss-feeds
no está fragmentada. En efecto:
=> (chunked-seq? (seq (range)))
true
=> (chunked-seq? (seq (get-rss-feeds r)))
false
Aquí está la fuente de get-rss-feeds
:
(defn get-rss-feeds
"returns a lazy seq of urls of all feeds; takes an html-resource from the enlive library"
[hr]
(map #(:href (:attrs %))
(filter #(rss-feed? (:type (:attrs %))) (html/select hr [:link])))
lo que parece que chunkiness depende de cómo se produce la SEC perezoso. Eché un vistazo al origen de la función range
y hay indicios de que se está implementando de una manera "gruesa". Así que estoy un poco confundido sobre cómo funciona esto. ¿Alguien puede aclarar?
He aquí por qué necesito saberlo.
tengo que siguiente código: (get-rss-entry (get-rss-feeds h-res) url)
La llamada a get-rss-feeds
devuelve una secuencia perezosa de URLs de los feeds que tengo que examinar.
La llamada a get-rss-entry
busca una entrada en particular (cuyo: campo de enlace coincide con el segundo argumento de get-rss-entry). Examina la secuencia diferida devuelta por get-rss-feeds
. La evaluación de cada elemento requiere una solicitud http en la red para obtener un nuevo feed rss. Para minimizar el número de solicitudes http, es importante examinar la secuencia una a una y detenerla tan pronto como haya una coincidencia.
Aquí está el código:
(defn get-rss-entry
[feeds url]
(ffirst (drop-while empty? (map #(entry-with-url % url) feeds))))
entry-with-url
devuelve una secuencia lenta de partidos o una secuencia vacía si no hay ninguna coincidencia.
Probé esto y parece funcionar correctamente (evaluando una URL de feed a la vez). Pero estoy preocupado de que en algún lugar, de alguna manera comience a comportarse de una manera "fornida" y comenzará a evaluar 32 avances a la vez. Sé que hay una manera de avoid chunky behavior as discussed here, pero parece que ni siquiera es necesario en este caso.
¿Estoy usando lazy seq non-idiomatically? ¿El bucle/repetición sería una mejor opción?
Parece ser que es una secuencia única "fragmentada" si utiliza las diversas funciones del pedazo en 'clojure.core' y/o su secuencia implementa el' IChunk' y 'IChunkedSeq' interfaces. Actualmente (en 1.4.0), estos no están documentados. – noahlz
¿Qué versión de clojure estás usando? –
Estoy usando Clojure v1.4 –