objekt-orientering og java

Post on 06-Jan-2016

48 Views

Category:

Documents

1 Downloads

Preview:

Click to see full reader

DESCRIPTION

Objekt-orientering og Java. Oppfriskning og videreføring av Java-kunnskaper. Forelesningen. Gjennomgang av grunnleggende begreper Klasser og objekter Kjøretidsmodell Spesielle Java-temaer Informasjonsskjuling Teknikker for strukturering av Java-kode Konvensjoner Refactoring-teknikker. - PowerPoint PPT Presentation

TRANSCRIPT

Objekt-orientering og Java

Oppfriskning og videreføringav Java-kunnskaper

Forelesningen• Gjennomgang av grunnleggende begreper

– Klasser og objekter– Kjøretidsmodell – Spesielle Java-temaer– Informasjonsskjuling

• Teknikker for strukturering av Java-kode– Konvensjoner– Refactoring-teknikker

Objekter og klasser• Objekter

– identitet: hvert objekt er unikt– har en tilstand i form av felt– innkapsling: tilgangen til tilstanden kan begrenses

• Klasser– beskriver generelle trekk ved objekter– mal for å lage nye objekter– metoder for å se på og endre objektene– klasser er også objekter:

har egen tilstand og egne metoder (og klasser!)

• Objekter har én klassetilhørighet livet gjennom• Klassen definerer hva et objekt ”kan”

#f34d:C1a = 1o = #f350

C1:Classb = 2o = #f34d

Objekter og identitet

• hvert objekt er unikt– tradisjonelt angitt med objektets adresse– identiteten kan kun sammenlignes med andre

• testes med ==-operator, e.g. o1 == o2• støtter ikke adresse-aritmetikk <=, >= og +, -

• likt innhold betyr ikke lik identitet– equals-metode, e.g. ”!”.equals(s)– ”!”.equals(”!”) er alltid sant– ”!” == ”!” kan være sant!

• vær varsom med egen equals-implementasjon– a.equals(b) => b.equals(a)– a.equals(b) => a.hashCode() == b.hashCode()

Identitet og referanser

• tilordning og parameteroverføring– skjer ALLTID vha. referanser (ulikt C og C++)– static boolean foo(Object o1, Object o2){ return o1 == o2;}String a = ”test”, b = a;

– både foo(a, a) og foo(a, b) er da sanne– referanser er begrenset til visse typer

• null– referanse til ingenting!– e.g. (a != null ? a.foo() : false)– alle objekt-variabler kan tilordnes/referer null-verdien

#f34d:Ca = 1o = #f350

Object o2

Object o2

Søppel og søppeltømming

• Objekter tar plass– hver type data tar en spesifikk mengde plass– objektets plass er omtrent summen av feltene– objekter er ”i live” så lenge referanser finnes

• Søppeltømming– referanser holder objekter ”i live”:Object o1 = new Object(), o2 = o1;

– hva skjer når siste referanse forsvinner:o1 = null; /* her? */o2 = null; /* her! */

– søppeltømmeren (GC) kommer og tar den!• Objekter tar plass og tømming tar tid

Ikke-objekt-verdier• Såkalte ”immediate/direkte values”

– tall (byte, int, float, double),brukes til aritmetikk

– tegn (char, e.g. ’c’),brukes i tekst og filbehandling

– sannhetsverdier (true, false),brukes i tester

• direkte verdier– tar liten plass, ikke pekere, overføres direkte– syntax for konstanter, e.g. 1, 3.1415, ’c’, true– maskinnære representasjoner og

raske operasjoner

1 3.14 ’c’true

Ikke-objekt-verdier...• Finnes også i objekt-drakt

– Integer:a = new Integer(1) => a.intValue() == 1

• ditto for Double/doubleValue(), Character/charValue(),– Boolean:true == new Boolean(true).booleanValue()

• bruk Boolean.TRUE/FALSE når Boolean-objekter trengs– Kan ikke endres, e.g. ikke støtte fornew Integer(1).setIntValue(2)

• Objekt-varianten er nyttig når:– trenger referanse til ingen verdi: null– referanse til flere typer verdier: Object eller Number– arrays (int[] vs. Integer[] og liste (List))

1 3.14 ’c’true

Arrays

• Deklarasjon– <type>[] <variabel>;– <type> <variabel>[];

• Initialisering– <variabel> = {<elt1>, <elt2>, <elt3>, ... ,};

• Tilordning– <variabel> = new <type>[<n>];– <variabel> = new <type>[] { <elt1>, <elt2>, <elt3>, ... , };

• Referanse– <variabel>[<n>]

• Casting– (<subtype>[])(<variabel av type>)– Integer i = ((Integer[ ])(objectArray))[0]; vs.– Integer i = (Integer)((objectArray)[0]);

java.lang.String

• Strenger er objekter– har identitet, lokal tilstand og metoder– e.g. s1 == s2 => s1.equals(s2), ikke omvendt– triks: ”hei”.equals(s), ikke omvendt pga. null

• Men: strenger kan ikke endres– s.charAt(0), men ikke s.setCharAt(0, ’c’)– betyr at like strenger kan slås sammen: ”t” == ”t”

• Implisitt kreasjon av nye strenger uten new– ”a” + ”b” gir ”ab”– ”1” + 2 gir ”12”– ”objekt: ” + s gir enten ”objekt: null” eller”objekt: ” + s.toString()

”Hello world” eller ”Hello world”

String gir lett mye søppel• java.lang.String er bygget på char[]• Strenger lages automatisk av +-operator

– String result = ””;for (int i = 0; i < 10; i++)

result = result + Integer.toString(i);– result.equals(”0123456789”) er sant– hver iterasjon lager nytt String-objekt og char[]!

• StringBuffer er et godt alternativ:– StringBuffer buf = new StringBuffer(10);for (int i = 0; i < 10; i++)

buf.append(i);String result = buf.toString();

– bruker mindre hukommelse og er raskere

Klasser og objekter• Klasser beskriver objekter

– felt / attributter– funksjoner / operasjoner / metoder

• Hvert objekt er av én klasse– skapes med new <klasse>(<parametre>)– klasse-objektet retureres av o.getClass()o = new <klasse>() =>o instanceof <klasse> &&o.getClass() == <klasse>.class

– nyttig ved debugging:– System.out.println(o.getClass() + ”:” + o);– objekter kan ALDRI skifte klasse

o må være != null

Klasse og objekt...

public class C1 {

public int f1;

public String f2;

}

Refererer til felt med dott-notasjon: c1.f1 og c1.f2;

Klassedefinisjon

Objekt

Identitet ogattributter

Klasse

#1234 : C1f1 = 10f2 = ”ti”

Arving

• en klasse kan bygge på en annen– nye felt og metoder legges til– metoder kan omdefineres

• objektene inneholder alle feltene– C2 arver fra C1:o = new C2() =>o instanceof C2 && o instanceof C1

– Men: o.getClass() == C2.class• variabler og referanser

– C1 o1 = new C1(); C2 o2 = new C2();– o1 = o2 er lov, men ikke o2 = o1

• casting (ikke fiske)– o1 = o2; o2 = (C2)o1; // lovlig sekvens!?!– typisk: if (o instanceof C2) ((C2)o).foo();

#f34d:C2f1 = 1f2 = ”hei”f3 = true

C1 o1

#f34d:C1f1 = 1f2 = ”hei”

C2 o2

Arving...

public class C2 extends C1 {

public boolean f3;

}

Klassedefinisjon

Objekt

}C1-del

} C2-del

superklassen

klasse

#2468 : C2f1 = 10f2 = ”ti”f3 = true

Arving...

C1 o1 = new C1();

C1 o2 = new C2();

C2 o3 = (C2)o2;

C1 o1

C1 o2

C2 o3

kun C1-del er synliggjennom o2}

lov, siden o2faktisk er C2

C2 o3 = (C2)o1; // ulovlig, gir ClassCastException

#2460 : C1f1 = 10f2 = ”ti”

#2468 : C2f1 = 10f2 = ”ti”f3 = true

Konstruktor-metoder og -kallpublic class C1 {

public int f1;public String f2;

}

public C1(int i, String s) {f1 = i;f2 = s;

}

Klassedefinisjon ogkonstruktor

new C1(10, ”ti”);

Konstruktor-kall ogobjekt

Identitet ogattributter

Først lages boksen av systemet,så kalles konstruktoren, som initialiserer feltene

#1234 : C1f1 = 10f2 = ”ti”

... konstruktor-metoderpublic class C1 {public int f1;public String f2;

}

public C1(int i, String s) {f1 = i;f2 = s;

}public C1(int i) {

this(i, ”???”);}public C1(String s) {

this(s.length());}

new C1(10, ”ti”);

En konstruktor kan kalle en annen,vha. this(<parametre>)-konstruksjonen

new C1(10);

new C1(”10”);

#1234 : C1f1 = 10f2 = ”ti”

#1234 : C1f1 = 2f2 = ”???”

#1234 : C1f1 = 10f2 = ”???”

Initialiseringskode

• Alternativ til konstruktorer• class C1 {

List l = new ArrayList();String lString = null;{

l.add(”en”);lString = l.toString();

}}

• Brukes typisk for å initialisere mer komplekse datastrukturer

• Kjøres automatisk før konstruktor-koden aktiveres

initialisering av verdi,kun uttrykk/expressions

generell kjørbar kode,kan referere til felt

Konstruktorer og arvingpublic class C2 extends C1 {

public boolean f3;

}

public C2(int i, String s, boolean b) {

super(i, s);

f3 = b;

}

Klassedefinisjon ogkonstruktor

new C2(10, ”ti”, true);

Konstruktor-kall ogobjekt

}C1-del

} C2-del

kall til superklassenskonstruktor

super-konstruktoren må kalles først,for å garantere gyldig tilstand

#2468 : C2f1 = 10f2 = ”ti”f3 = true

Metoder

• Funksjoner / operasjoner / metoder– kode som utføre ”inni” objektet– <referanse>.<metodenavn>(<parametre>), e.g. o.toString()– tilsynelatende som referanse til felt (funksjon som feltverdi!)– kan referere direkte til objektets tilstand

• public String toString() {return ”f1= ” + f1 + ”, f2: ” + f2;

}• new C1(”10”).toString() => ”f1=2, f2: ???”• public String toString(String prefix) {

return prefix + toString(); }

Metoder forts.

void foo(int delta) {f1 += delta;f3 = ! f3;

}foo(1);

void foo(int f1) {this.f1 = f1;f3 = ! f3;

}foo(11);

#2468 : C2f1 = 10f2 = ”ti”f3 = true

#2468 : C2f1 = 11f2 = ”ti”f3 = false

Metoder...

void foo(int f1) {

this.f1 = f1;

f3 = ! f3;

}

foo(11);

this

#2468 : C2f1 = 10f2 = ”ti”f3 = true

foo : C2this = #2468f1 = 11

#2468 : C2f1 = 10f2 = ”ti”f3 = true

foof1 = 11

Metoder...

• Klasse Aboolean b;bar(int i) { b = (i == 2); }foo(int f) { bar(f+1)}

: B

fooa =

: Ab =

foof = 1

bari = 2

: Ab = true

• Klasse Bfoo(A a) { a.foo(1); }

• new B().foo(new A());

: B

: A

Metoder og arvingclass C1 {

int f1 = 0;void foo(int delta) {

f1+=delta;}

}

class C2 extends C1 {void foo(int delta) {

f1+=delta;super.foo(delta);

}}new C2().foo(2);

this

#2468 : C2f1 = 0foo = (int)foo = (int)

foodelta

super

f1 = ?

Metoder og arving...class C1 {

void foo(int i) { bar(i); }void bar(int i) { ... }

}

class C2 extends C1 {void foo(int i) {

super.foo(i);super.bar(i);

}void bar(int i) { ... }

}new C2().foo(2);

vs.

#2468 : C2foo = (int)bar = (int)foo = (int)bar = (int)

foo : C2i

foo : C1i

Sekvens:C2.foo, C1.foo, C2.bar, C1.bar

Polymorfi• Metodesignatur

– typene til parametrene– retur-verdien(?)– eks. public void drawString(String, int, int)

• Metodekall– typene til parametrene må stemme med

metodesignaturen– f.eks. drawString(”Hello world”, 10, 10+10)

• Automatiske konvertering av typer– int til double og float– s + o => s + o.toString(),

s + i => s + Integer.toString(i)

Polymorfi...

• Samme metodenavn, ulik signatur– teknisk sett ulike metoder– bør ha ”samme” bruk– public int parseInt(String s, int base) { ... } og

public int parseInt(String s) { parseInt(s, 10);}– tilsvarende for konstruktorer (<init>)

• Bruk når en vil– unngå for mange ulike navnevariasjoner– gjøre API’er hendigere å bruke

Grensesnitt

• Metoder = garanti om evner• Algoritmer

– formuleres vha. sett av metoder: ”dersom du kan dette, kan jeg gjøre ... med deg”

– et objekt har en ”rolle” ift. algoritmen– den egentlige klassen spiller ingen rolle,

bare disse metodene er implementert• Klassisk eksempel: sortering

– krever mulighet for skanning og sammenligning– to typiske grensesnitt: List og Comparator

• List: int size, Object get, void add, void remove, ...• Comparator: int compare, boolean equals

– sorteringsalgoritmen trenger kun disse som støtte

Grensesnitt...

• Metoder krever:– objekter som kan visse ting

• Objekter tilbyr:– sett med metoder

• Interface-definisjoner– samler relevante sett med metoder/evner– klasser signaliserer at de implementerer dem– objekter av klasser som implementerer List, kan

brukes overalt hvor en List kreves– en klasse kan implementere flere grensesnitt, dvs.

inneha flere roller

Grensesnitt i Java

• public interface List {public int size();public boolean contains(Object o);public Object get(int i);

public void set(int i, Object o);}

• public interface Comparator {// o1 < o2 gir -1, o1 = o2 gir 0, og o1 > o2 gir 1 public int compare(Object o1, Object o2);

}• Collection.sort(List, Comparator);

Grensesnitt i Java...• public class IntegerList implements List, Comparator {

public int size() { ... }public boolean contains(Object o) { ... }public Object get(int i) { ... } // egentlig Integer

public void set(int i, Object o) { ... } // egentlig Integer

public int compare(Object o1, Object o2) { int i1 = ((Integer)o).intValue(), i2 = <

(Integer)o).intValue(); if (i1 < i2) return -1; else if (i1 > i2) return 1; else return 0;}

}• IntegerList il = new IntegerList(); add(il, ...); add (il, ...), ...• Collections.sort(il, il); // sorter liste, med spesifikk sammenligning

Abstrakte klasser

• Deklarerer visse evner

• Implementerer dem ikke alle selv

• Kan ikke lage objekter fra klasse

• ”Delvis implementert klasse”,subklasser må implementere resten

• Sier eksplisitt hvilke som mangler

• Kan arve metoder (forplikte seg), uten å implementere disse

Abstrakte klasser...

• public abstract class AbstractList implements List {public boolean contains(Object o) {

for (int i =0; i < size(); i++)if (get(i).equals(o)) return true;

return false;}// resten av metodene er implisitt abstrakte f.eks.public abstract int size(); // kun deklarasjon, ingen

implementasjon...

}• Grensesnitt tilsvarer abstrakt klasse med kun abstrakte

metoder (Merk: implements vs. extends)

Grensesnitt-konstanter

• Arve av grensesnitt– arv innebærer forpliktelse,

ikke gjenbruk av kode– sub-klasse i praksis uavhengig av grensesnitt

• Arv av konstanter– grensesnitt kan deklarere konstanter av innebygde

type (integer, char, etc.)– konstantene kan nås gjennom sub-klasse

• Eks. SwingConstants– LEFT/CENTER/RIGHT, TOP/MIDDLE/BOTTOM

Synlighet av navn

• Grensesnitt– gir frihet til reimplementasjon uten endring av

ytre forpliktelser

• Innkapsling– skjul alt som utsiden ikke trenger å vite

• Mekanisme– redusere synlighet av navn

• Kunst å la akkurat passe mye være synlig

Synlighet av navn...

• ”public”– navn er synlig for alle

• felt og metoder ut av klasse• klasse ut av pakke(/klasse)

– implisitt i interface-definisjoner– mål å redusere mengden public-navn– reduserer frihet til å endre ting siden

• ”private”– navn er ikke synlig

• felt og metoder synes ikke utenfor klasse• klasse synes ikke utenfor pakke(/klasse)

Synlighet av navn...

• ”protected”– navn er synlig for sub-klasser, via arv– delvis eksponering av detaljer– brukes ofte til hjelpemetoder,

f.eks. vanlig i abstrakte klasser– gir mulighet til mer effektive sub-klasser– kan gi utilsiktede bindinger

• ”” = pakke-privat– navn inni klasse synlig for alle klasser i samme pakke– brukes blant tett koblede klasser– vanligvis ikke nødvendig

Pakker i Java

• Samler sammenhørende klasser• Gjør det lettere å holde oversikt over store API’er• Hierarkisk pakke-struktur

– java.lang. - grunnleggende klasser f.eks. Integer, String– java.util. – nyttige hjelpeklasser, f.eks. List– java.awt. – ”gamle” GUI-klasser (inkl. java.awt.event.)– javax.swing. – ”moderne” GUI-klasser (javax angir java-utvidelse)– javax.swing.tree – klasser knyttet til JTree (men ikke JTree selv)– ...

• Tilsvarer mappestruktur Meget viktig– filnavn = klassenavn– mappe = pakke– mappehierarki = pakkehierarki

Pakker i Java...

• En klasses egentlige navn inneholder pakkenavnet– java.lang.String– java.util.List– javax.swing.JTree;

• To måter å referere til en klasse– fullt navn, f.eks. java.lang.List– kombinasjon av import og kortnavn

• import java.lang.List;• List l = new java.util.ArrayList();

• import– samles i toppen av fil (før klassedeklarasjonen)– liste med import-setninger gir nyttig oversikt over avhengigheter– importere hele pakker vha. import <pakkenavn>.*;

Jar-filer• Java ARchive

– enkeltfil med mappestruktur inni– innpakning av applikasjons pakkestruktur

• Kjøring av Java-applikasjon krever– tilgang til mappestruktur med .class-filer (kompilerte java-filer)– jar-fil med tilsvarende katalogstruktur

• CLASSPATH (eller –classpath/cp direktiv)– refererer til nødvendige mapper og jar-filer– refererer til mappen som inneholder toppnivå-pakken– må være komplett, slik at alle klasser kan lokaliseres

• java –cp vips/classes;jar1.jar;jar2.jar– vanlig at prosjektmappe inneholde src-mappe– kompiler til classes-mappe

Static-modifikator

1. Klasse som mal for objekter– identitet, feltverdier og initialiseringskode– konstruktorer og metoder håndterer tilstanden

2. Klassen er også selv et objekt– har navn, ikke identitet– har felt og initialiseringskode– har metoder, men ikke konstruktorer

• ”Static” angir felt, kode og metoder av type 2• Kode kjører i kontekst av klasse, ikke objekt• ”vanlige” klasser er implisitt static

Static-modifikator...

• class C {private static List allCs = new ArrayList();public C() {

allCs.add(this);}public static List getAll() { return allCs;}

}• new C();• C.getAll().size() == 1; C:Class

allCs =

#:ArrayList

#:Cclass

Nøstede klasser

• Klasser inni klasser– klasse C1 er konteksten til klasse C2– to tilfeller, med eller uten static

• Static indre-klasse– som vanlig klasse, men spesiell type synlighet– dott-notasjon brukes for benevning

• C1.C2 objekt = new C1.C2();

– greit å bruke for å samle kode i en fil

Indre-klasser

• Klasse (C2) definert inni annen klasse (C1)– kode i C2 ser navn definert i C1– C2 arver ikke fra C1, men kan arve fra andre

• C2-objekter– inneholder som vanlig egne og

arvede egenskaper– eksisterer alltid i konteksten av C1-objekt– kan referere direkte eller indirekt til C1 sine egenskaper

• Bruksområder– et objekt uløselig knyttet til ett annet objekt– behov for å skjule klassen

Indre-klasser...

• public class C1 {String n = ””;public C1(String s){ n = s;}

public class C2 {public C2() { ... }public getName(){ return n;}

}public C2 createC2() {

return new C2();}

}• new C1(”hal”).createC2().getName() => ”hal”

#:C1n = ”hal”

createC2

#:C2

getName

C1

implisitt referanse tilkontekst-objekt

Komplisert tilfelle

• public class C1 {String n = ””;public C1(String s){ n = s;}

public class C2 extends C1 {public C2(String s){ super(s); }public getName(){ return this.C1.n + n;}

}public C2 createC2(String n){ return new C2(n);}

}• new C1(”hal”).createC2(”9000”).getName() => ”hal9000”

#:C1n = ”hal”

createC2getName

C1 #:C2n = ”hal”

thisthis

”ser” C1 fra to kanter

kontekstuelt felt vs. arvet

Anonyme indre-klasser

• Indre-klasse– har annen klasse som kontekst– arver (extends) eller implementerer (implements)

annen klasse• Anonym variant

– navnløs klasse defineres i konstruktor-kall– direkte (re)implementasjon av metoder

• To typer bruk– direkte implementasjon av grensesnitt– variant av eksisterende (evt. abstrakt) klasse

• Svært hendig, men kan virke forkludrende

Anonyme indre-klasser...

• List l = new ArrayList();• ...• Collection.sort(l, new Comparator() {

// implementasjon av metodepublic int compare(Object o1, Object o2) {

return o1.toString().compareTo(o2);}

}); // vanlig å glemme

Anonyme indre-klasser...

• public class MyFrame extends JFrame {public MyFrame() {

add(new JPanel() {public void paint(Graphics g) {

System.out.println(”paint!”);}})

}}

Anonyme indre-klasser...

• public class MouseAdapter implements MouseListener {// dummy-metoder, gjør ingentingpublic void mousePressed(MouseEvent event) { }public void mouseReleased(MouseEvent event) { }public void mouseClicked(MouseEvent event) { }

}• public class MyPanel extends JPanel {

public MyPanel() { addMouseListener(new MouseAdapter() { public void mouseClicked(MouseEvent e) {

System.out.println(”Click!”); }});}

}

Anonyme indre-klasser...

• add(new JButton(new AbstractAction(”OK”) {public void actionPerformed(ActionEvent

ae) {// alt som må gjøre// når OK-knappen trykkes

}}));

• Anonym klasse er indre-klasse inni annen klasse• Kode-kroppen vil typisk kalle metoder i kontekst-

objektet

Anonyme indre-klasser...

• public class MyPanel extends JPanel {public MyPanel() {

add(new Button(new AbstractAction() { ... }));

}public doOK(ActionEvent ae) { ... }

}

#:MyPaneldoOK = (ActionEvent)

actionPerformed

MyPanel #: AbstractActionactionPerformed = (ActionEvent)

this

Anonyme indre-klasser...• Anonyme indre-klasser kan også referere til

– kontekst-objektets felt– variable definert i metoder (!)

• Disse må være deklarert som final,som garanterer at de ikke endres

• public void addButton(final String s) { add(new Button(new AbstractAction(s) { public void actionPerformed(ActionEvent ae) { doButton(ae, s); } })); } public doButton(ActionEvent ae, String s) { System.out.println(s + ”-knappen ble trykket ned”); }}

Anonyme indre-klasser...

• Det er som om konteksten er metoden hvor den anonyme klassen er definert

#:MyPaneldoOK = (ActionEvent)

actionPerformedae = ActionEvent

MyPanel #: extends AbstractActionactionPerformed = (ActionEvent)

this

addButtons = ”OK”

this

Anonyme indre-klasser...

• final-deklarasjonen sikrer at variabel-verdien kan kopieres og dermed overleve addButton-kallet

#:MyPaneldoOK = (ActionEvent)

actionPerformedae = ActionEvent

MyPanel #: extends AbstractActionactionPerformed = (ActionEvent)<kopi av> s = ”OK”

thisaddButtons = ”OK”

this

Strukturering av Java-kode

• Konvensjoner– navngiving– sammenhørede metoder

• ”Sunne” strukturer– lettere å forstå og jobbe med– fleksible i bruk– ”patterns”

Navnekonvensjoner

• Feltnavn– enkelt-objekter angis med entall– arrays og lister angis med flertall

• Accessorer– getter: lese felt x med getX()– setter: sette felt x med setX(<type>)– adder: legge til felt xs med addX(<type>)– remover: fjerne fra xs med removeX(<type>)

• Ekkel blanding av norsk og engelsk?

Navnekonvensjoner...

• Hendelser– XEvent– fireXEvent

• Lyttere– XListener-klasse– xChanged(XEvent)-metode– addXListener-metode– removeXListener-metode

Delegering

• Viktigste OO-prinsipp etter arv– Moderne rammeverk bruker grensesnitt og delegering, i mindre

grad arv

• Grunnidé:– en logisk funksjon legges til ny klasse– metoder kopieres over– felt innføres, som refererer til ny klasse– metoder ”delegerer” til objekt

• Fordel– logisk avgrensing av funksjon– reduserer kompleksitet i klasse– oppførsel kan endres ved kjøretid, ved å bytte instans

Delegering...

• Komponent har mange funksjoner– hierarki– hendelseshåndtering– tegning av ramme og innhold

• Ny Border-klasse– paintBorder og getBorderSize-metoder– border-felt og get/setBorder-metoder– internt kalles border.paintBorder

• Eller enda bedre– Border-grensesnitt (og evt. AbstractBorder-klasse)– Mange ulike Border-implementasjoner

Delegering...

• Grunnlag for MVC-arkitektur– metoder for datahåndtering

delegeres til Model-klasse– metoder for ”rendering”

delegeres til View-klasse– metoder for input

delegeres til Controller-klasse

• Samles i åpent tilgjengelig klasse• Tre grensesnitt, mange implementasjoner• Grunnlag for Swing-komponenter, ikke rendyrket

top related