Delegeringsteknikken Delegering er en teknikk hvor et objekt tilbyr et sett metoder og bruker et internt objekt til å utføre logikken, dvs. delegerer oppgaven til det interne objektet. Delegering i det virkelige liv handler om at én person kan ta ansvar for å utføre noe for en oppdragsgiver, men overlater til den annen (delegaten) å gjøre selve jobben uten at dette (nødvendigvis) synliggjøres for oppdragsgiveren. Den som delegerer (den delegerende) får evner til å utføre oppgaver, basert på delegatens evner og ens myndighet over denne. Denne rollefordelingen er også nyttig innen objekientering: et objekt benytter seg av et annet for å utføre en del av en tjeneste. En typisk bruk av delegering er for å realisere en 1-n-assosiasjon, som er kapslet inn med metoder for å lese antall elementer, hente ut et bestemt element basert på indeks og legge til og fjerne elementer. Ta CD- og Track-klassene og tracks-koblingen som eksempel: class CD private List<Tra ck tracks = t<track (); int gettrack Count() size(); Track gettrack (int index) Klassediagrammet og koden til venstre viser hvordan tracks- assosiasjonen er realisert. Vi ser at den er kapslet inn med en rekke metoder og at realiseringen bruker en intern t. Alle innkapslingsmetodene kaller bare tilsvarende metoder i t- objektet, uten noe særlig mer logikk. Vi sier at CD delegerer til Ar raylist. Sekvensdiagrammet til høyre illustrerer hvordan CD- objektet bruker t-objektet. Selv om vi hadde lagt til litt validering og annen logikk, så hadde alt grovarbeidet i praksis blitt utført av t-klassen, og uten å delegere og dermed (gjen) bruke logikken i t-klassen, så ville CD-klassen blitt mye mer kompleks. Dette er typisk for delegeringsteknikken: Den delegerende klassen har et internt objekt av delegat-klassen, altså objektet som det delegeres til, som gjør det meste av grovarbeidet. Den delegerende klassen har metoder med samme eller lignende navn som metoder i del egat-klassens. Disse metodene delegerer mer eller mindre direkte til metoder i d elegat-objektet. Sekvensdiagrammet illustrerer den generelle teknikken godt, bare bytt ut CD med delegerende og ArrayLi st med delegat. get (index); void addtrack (Track track)
if (! contains (track)) add (track); void removetr ack (Track track) remove (track); I dette tilfellet er det faktum at en bruker delegering ikke på noen måte synlig utenifra, fordi det t-objektet opprettes internt i klassen og det gis ingen direkte tilgangen til det, siden det jo er kapslet inn. Men i mange tilfeller er litt av poenget at en utenifra kan styre hvilket objekt det delegeres til og dermed påvirke totaloppførselen. Dette illustreres av følgende eksempel. Vi skal lage en som går gjennom (genererer) annenhvert element i en liste, men istedenfor å knytte den direkte til en List (eller Collection/Iterable), så lar vi den delegere til en annen : class implemen ts Itera private Itera ; Vi ser at hvert kall til ) vil resultere i et kall til ) på de legaten ( ). Hvert kall vil next() vil imidlertid gi først et kall til next() på delgaten og så et kall til ) og evt. et nytt kall til next(). Effekten av det andre kallet til next() er å bruke opp / hoppe over annenhvert element: det første elementet brukes, det andre kastes, det tredje brukes og det fjerde kastes osv. ) - kallet er der for å unngå å utløse unntak ved at vi hopper over et element som ikke finnes. Et viktig poeng her, ut over bruken av delegering, er at konstruktøren tar inn delegaten, slik at den som bruker, kan bestemme hvilken det delegeres til, dvs. hvor elementene egentlig kommer fra. I følgende kode-eksempel kommer elementene fra en vanlig liste:
(Iterato r<object ) this. = ; @Overrid e boolean ). ); @Overrid e Object next() Object o =.next(); if (iterato rdelegat e. List<Obj ect list = t<object (Arrays. aslist (1, 2, 3, 4, 5, 6)); produces every second element in list Itera it2 = (list. ()); prints 1 3 5 while System. out. print next() + " "); En -instans kan delegere til en annen EverySe c, for dermed å hoppe over flere elementer:
.next(); o; List<Obj ect list = t<object (Arrays. aslist (1, 2, 3, 4, 5, 6, 7, 8, 9)); produces every fourth element in list Itera it2 = ( (list. ())); prints 1 5 9 while System. out. println next() + " ");
Sidetype Ferdig Dekningsgrad Omfang teori 25 25 25