sql - multiple - Implementar DISTINCT para la comprensión.
select distinct sql server ejemplos (1)
¿Hay una manera de referirse desde una cláusula de filtro de la misma comprensión a los elementos que ya se han cedido?
Tu para la desugars de comprensión a algo más o menos parecido.
pathSets flatMap {
pathSet => pathSet filter {
path => path.endState contains target
}
} map {path => path}
El último mapa con una función de identidad es su rendimiento. No puedo recordar si la especificación permite que ese mapa se elimine cuando se trata de una función de identidad.
De todos modos, espero que esto muestre más claramente por qué no hay un "regreso" con esa estructura.
Puedes escribir una función distinta, recursiva y perezosa
implicit class DistinctStream[T](s: Stream[T]) {
def distinctBy[V](f: T => V): Stream[T] = {
def distinctBy(remainder: Stream[T], seen:Set[V]): Stream[T] =
remainder match {
case head #:: tail =>
val value = f(head)
if (seen contains value) distinctBy(tail, seen)
else Stream.cons(head, distinctBy(tail, seen + value))
case empty => empty
}
distinctBy(s, Set())
}
}
Y usalo asi
def solutions(target: Int): Stream[Path] =
(for {
pathSet <- pathSets
path <- pathSet
if path.endState contains target
} yield path) distinctBy (_.endState)
Sí, ahora hay recursión. Pero ya existía porque las funciones map, flatMap y filter de Stream ya son funciones recursivas perezosas.
En la penúltima conferencia de su curso de Coursera , el profesor Odersky ofreció lo siguiente for
comprensión como el paso final en un estudio de caso encantador:
def solutions(target: Int): Stream[Path] =
for {
pathSet <- pathSets
path <- pathSet
if path.endState contains target
} yield path
En una conferencia anterior él dibujó algunas analogías entre comprensiones y SQL.
Lo que estoy buscando es una forma de yield
solo aquellas path
que tienen un estado endState
.
¿Hay una manera de referirse desde una cláusula de filtro de la misma comprensión a los elementos que ya se han cedido?
Otro enfoque podría ser convertir pathSets
en un Map
de endState
a path
antes de la instrucción for
, luego volver a convertirlo en un Stream
antes de devolverlo. Sin embargo, esto parece perder los beneficios de la perezosa computación de usar un Stream
.
Un método anterior del mismo estudio de caso logró objetivos similares, pero ya era una función recursiva, mientras que este no necesita (parece) ser recursivo.
Parece que podría usar un Set
mutable para rastrear los endState
que se obtienen, pero eso no es satisfactorio, ya que el curso ha evitado el uso de la mutabilidad hasta el momento.