Czy istnieje sposób użycia systemu typu Scala, aby zwięźle określić kontekstowy podgraph kompletnego wykresu obiektu?Czy Scala może ograniczać wykres obiektów, aby widoczne były tylko te obiekty, które są istotne dla kontekstu?
DCI twierdzi, że często masz dość złożony wykres obiektów, ale w każdym przypadku użycia często chcesz pracować tylko z pod-grafem. Masz numer Foo
, który ma Bar
i Bat
, ale gdy używasz obudowy 1, interesuje Cię tylko wersja Bar
, a w przypadku 2 używana jest tylko wersja Bat
.
Na przykład, powiedzmy, że masz tę strukturę, a Role1 use-case wymaga Foo->Bar->Baz->Bin
i Role2 use-case wymaga Foo->Bat->Baz->Buz
:
class Foo{
val bar = new Bar() //Only relevant to Role 1
val bat = new Bat() //Only relevant to Role 2
}
class Bar {
val baz = new Baz()
}
class Bat {
val baz = new Baz()
}
//Relevant to both Role 1 and 2 (via Bar or Bat)
class Baz {
val bin = new Bin() //Only relevant to Role 1
val buz = new Buz() //Only relevant to Role 2
}
class Bin{}
class Buz{}
Łatwo jest zobaczyć, jak można ograniczyć dostęp w się pojedyncza klasa przez korzystających cech:
trait FooInRole1 { def bar : Bar } //Define accessor in trait
s/Foo/Foo extends FooInRole1/ //Change Foo's declaration to implement trait
val f : FooInRole1 = new Foo //LHS is i'face, RHS is implementation
//f.bat <--Compile error Irrelevant field is not available. \o/
Ale trzeba powtórzyć ten wzór dla każdego obiektu istotne warstwa użytkowa walizka. (Na przykład, trzeba mieć dostęp do bin
BazInRole1
i BazInRole2
dostęp do biz
)
Moje pytanie brzmi, czy istnieje jakiś sposób, aby uniknąć pisania tych wszystkich cech jest łatwy do zdobycia, tak, przestrzeni nazw wyparcia. Na przykład, można sobie wyobrazić coś takiego kodu (które nie skompilować):
class Foo[T] {
T match {
case r1 : Role1 => def bar : Bar[T]
case r2 : Role2 => def bat : Bat[T]
case _ => //Nothing
}
}
val fInRole1 = new Foo[Role1] //Provides Foo->Bar->Baz->Bin
val fInRole2 = new Foo[Role2] //Provides Foo->Bat->Baz->Buz
Wygląda typu systemu Scala jest na tyle wyrazisty, aby zrobić coś takiego, ale nie mogę zrozumieć.
Myślę, że coś takiego można osiągnąć dzięki klasom typów. Po prostu utwórz klasę typu widok na grafie obiektu i uzyskaj dostęp do zawartości i manipuluj jej zawartością tylko poprzez klasę typów. – ziggystar