Skip to content

Latest commit

 

History

History
93 lines (80 loc) · 3.15 KB

inner-classes.md

File metadata and controls

93 lines (80 loc) · 3.15 KB
layouttitlelanguagepartofnumnext-pageprevious-page
tour
Unutarnje klase
ba
scala-tour
22
abstract-type-members
lower-type-bounds

U Scali je moguće da klase imaju druge klase kao članove. Nasuprot jezicima sličnim Javi, gdje su unutarnje klase članovi vanjske klase, u Scali takve unutarnje klase su vezane za vanjski objekt. Pretpostavimo da želimo da nas kompejler spriječi da pomiješamo koji čvorovi pripadaju kojem grafu. Tipovi zavisni od putanje (en. path-dependent) omogućuju rješenje.

Radi ilustracije razlike, prikazaćemo implementaciju klase grafa:

classGraph { classNode { varconnectedNodes:List[Node] =NildefconnectTo(node: Node):Unit= { if (!connectedNodes.exists(node.equals)) { connectedNodes = node :: connectedNodes } } } varnodes:List[Node] =NildefnewNode:Node= { valres=newNode nodes = res :: nodes res } }

U našem programu, grafovi su predstavljeni listom čvorova (List[Node]). Svaki čvor ima listu drugih čvorova s kojima je povezan (connectedNodes). Klasa Node je path-dependent tip jer je ugniježdena u klasi Graph. Stoga, svi čvorovi u connectedNodes moraju biti kreirani koristeći newNode iz iste instance klase Graph.

valgraph1:Graph=newGraphvalnode1: graph1.Node= graph1.newNode valnode2: graph1.Node= graph1.newNode valnode3: graph1.Node= graph1.newNode node1.connectTo(node2) node3.connectTo(node1)

Eksplicitno smo deklarisali tip node1, node2, i node3 kao graph1.Node zbog jasnosti ali ga je kompajler mogao sam zaključiti. Pošto kada pozivamo graph1.newNode koja poziva new Node, metoda koristi instancu Node specifičnu instanci graph1.

Da imamo dva grafa, sistem tipova Scale ne dozvoljava miješanje čvorova definisanih u različitim grafovima, jer čvorovi različitih grafova imaju različit tip. Ovo je primjer netačnog programa:

valgraph1:Graph=newGraphvalnode1: graph1.Node= graph1.newNode valnode2: graph1.Node= graph1.newNode node1.connectTo(node2) // legalvalgraph2:Graph=newGraphvalnode3: graph2.Node= graph2.newNode node1.connectTo(node3) // illegal!

Tip graph1.Node je različit od graph2.Node. U Javi bi zadnja linija prethodnog primjera bila tačna. Za čvorove oba grafa, Java bi dodijelila isti tip Graph.Node; npr. Node bi imala prefiks klase Graph. U Scali takav tip je također moguće izraziti, piše se kao Graph#Node. Ako želimo povezati čvorove različitih grafova, moramo promijeniti definiciju naše inicijalne implementacije grafa:

classGraph { classNode { varconnectedNodes:List[Graph#Node] =NildefconnectTo(node: Graph#Node):Unit= { if (!connectedNodes.exists(node.equals)) { connectedNodes = node :: connectedNodes } } } varnodes:List[Node] =NildefnewNode:Node= { valres=newNode nodes = res :: nodes res } }

Primijetite da ovaj program ne dozvoljava da dodamo čvor u dva različita grafa. Ako bi htjeli ukloniti i ovo ograničenje, moramo promijeniti tipski parametar nodes u Graph#Node.

close