mam niezmienną strukturę danych gdzie mam zagnieżdżony wartości w mapach, tak:Unikanie powtarzania za pomocą soczewek podczas głębokiego kopiowania na Mapie wartości
case class TradingDay(syms: Map[String, SymDay] = Map.empty)
case class SymDay(sym: String, traders: Map[String, TraderSymDay] = Map.empty)
case class TraderSymDay(trader: String, sym: String, trades: List[Trade] = Nil)
osobno Mam listę wszystkich transakcji ponad dzień, i chcę, aby wygenerować strukturę TradingDay
, gdzie
case class Trade(sym: String, trader: String, qty: Int)
próbuję dowiedzieć się, w jaki sposób mogę zaktualizować tę strukturę z soczewek (patrz załącznik) poprzez składanie przez moich transakcji:
(TradingDay() /: trades) { (trd, d) =>
def sym = trd.sym
def trader = trd.trader
import TradingDay._
import SymDay._
import TraderSymDay._
val mod =
for {
_ <- (Syms member sym).mods(
_ orElse some(SymDay(sym)))
_ <- (Syms at sym andThen Traders member trader).mods(
_ orElse some(TraderSymDay(trader, sym)))
_ <- (Syms at sym andThen (Traders at trader) andThen Trades).mods(
trd :: _)
x <- init
} yield x
mod ! d
}
To działa; ale zastanawiam się, czy mógłbym być mniej powtarzalny (jeśli chodzi o dodawanie do mapy, a następnie modyfikowanie wartości w kluczu mapy, nie wydaje się to o wiele mniej irytujące niż powiązana z nią głęboka kopia.)
Dodatek - soczewki
object TradingDay {
val Syms = Lens[TradingDay, Map[String, SymDay]](_.syms, (d, s) => d.copy(syms = s))
}
object SymDay {
val Traders = Lens[SymDay, Map[String, TraderSymDay]](_.traders, (d, t) => d.copy(traders = t))
}
object TraderSymDay {
val Trades = Lens[TraderSymDay, List[Trade]](_.trades, (d, f) => d.copy(trades = f))
}
+1 na pytanie z dodatku – ziggystar