referenzen - kstu...mitarbeiter m4; m4.geha1t ~ 4000; 1/ compi1e-fehler in abbildung 11.2 ist die...

32
11 Referenzen Variablen primitiven Dat entyps und Ohj eten-ariaht en unte rscheiden sich in tcchni- sch e r Hinsicht deutlich. Dies betrifft insbeson dered en Effekt vo n J: 1I11 'dsI/Jlg en und die An de r rarametcr nbergabc an Meth oden. Im Gegensatz zu primitiven Dat entypen handelt es sich bei Objektvariabl en UIll so- ge nan nte Rej eren zell. Dies impliziert. da ss zwischen de r Objektva riablen lind dem von ihr bez eich net en Obj ekt unt e rsc-hie den werd en muss. Das wichtige K onzept des Xei Rers (c- ngl. poinrer) ist die mfo rnumo nstcchntschc Gru ndlage d er folgenden Berracbrungen. Im Gegensatz zu C++ kennt Java keine ex- plizit en echten Zeiger. J ed och stellen alle deklar i erte n un d mitialisicrten java- Obj ekt variablen Referenzen auf die zugehörigen Objekte dar. Bei Zuwei sungen und Param et erübergaben verhalten sich Objektr eferen zen wie Zeiger, so dass auch in Ja- va nicht auf das Verständnis des Zeigerkon zepts verzichtet werden kann. 11.1 Primitive Datentypen Um das beso ndere Verhallen von Obj ektrefe re nz en besser zu verstehe n, we rden no chmals die korres pon die r enden Eigenschaft en p rimitive r Dat entypen genan nt. 11.1.1 Zuwei sungen primitiver Datentypen Nach Zuweisung eines werts enthält eine variable der primitiven java-Darent ypc n byte, short , char, in t,long,float, doub le und boo lean gcnau die sen zu- gewi esene nWen. Der Variablenname be zeichnet einen Bereich im I Iaupt spcichcr, in dem der We rt der Variablen ge speichert ist. Zuwe isungen zw isc hen va riablen primit iven Datentyps geschehen ausschließlich per wents opte Sofern die Typen zu- we ts ungskom pattlx -l sind, wird der aktuelle Wert der einen Variablen einfach in die an dere Variable kop iert: int a .. 400 ; int b = a; a .. 100 ; Die Variable b ernhält nach de r Zuwei sung b=a den Wert 400. Die nachträgliche Änderung des Werts von a auf 100 beeinflusst b nicht. Auch nach der Zmveisung b =a beze i chnen die Namen a und b unterschiedliche Variablen, deren ind ividuell belegbare Weite an unt erschiedlichen Speic herad ressen verwaltet werden: Der Wenzu griff über eine Variable kann den w ert der anderen Variablen nicht bee tnfl us- sen. Kons equenz f ür die Programmieru ng iSI, dass Zuweisungen zwischen Variablen primitiven Datentyps un problematisch sind: Nacht rägliche Wertänderungen einer Va- riablen hat keinen Nebeneffekt für den Wert anderer variablen. Durch den Vergleichsoperator == könn en Variablen primitiven Datentyps dir ekt ve r- glichen werden : a==b ist erfüllt, wenn a und b de n gleichen 'lXb1 tragen .

Upload: others

Post on 08-Feb-2021

2 views

Category:

Documents


0 download

TRANSCRIPT

  • 11 ReferenzenVariablen primitiven Datentyps un d Ohjeten-ariahten unte rscheiden sich in tcchni-sche r Hinsicht deutlich. Dies betrifft insbesondere den Effekt vo n J:1I11 'dsI/Jlg en unddie An der rarametcrnbergabc an Methoden.

    Im Gegensatz zu primitiven Datentypen ha ndelt es sich bei Objektvariablen UIll so-ge nannte Rej erenzell. Dies impliziert. da ss zwischen der Objektvariablen lind de mvon ihr bez eichneten Obj ekt unt e rsc-hieden werden muss .

    Das wichtige Konzept des XeiRers (c-ngl. po inrer) ist die mfo rnumo nstcchntschcGru ndlage der folgend en Berracb runge n. Im Gegensatz zu C++ kennt Java kein e ex-pliziten echten Zeiger. Jedoch stellen alle deklarierten un d mitialisicrten j ava-Objektvariablen Referenzen auf d ie zugehö rigen Objekte dar. Bei Zuweisungen undParam eterübergaben verhalten sich Obj ekt referenzen wie Zeiger, so da ss auch in Ja-va nicht au f das Verstän dnis des Zeigerk on zept s verzichte t werden kann.

    11.1 Primitive DatentypenUm da s besondere Verhallen vo n Objektrefe renzen besser zu verstehe n, we rdennochmals die korres pondie renden Eigenschaften primitive r Datentypen genannt.

    11.1.1 Zuweisungen primitiver Datentypen

    Nach Zuweisung eines w erts enthält e ine variable der primitiven java-Darentypcnbyte, short , char, in t , l on g , f l o a t , doub l e un d boolean gcnau d iesen zu-gewiesenen Wen. Der Variab lenname bezeichnet e inen Bere ich im IIauptspcichcr,in dem der We rt der Variablen gespeichert ist. Zuwe isungen zwisc hen va riablenprimit iven Datentyps gesche he n ausschließlich per wentsopte Sofern die Typen zu-we tsungskompattlx -l sind, wird de r aktuelle Wert der e ine n Variablen einfach in diean dere Variable kopiert:

    i n t a .. 400 ; int b = a ; a .. 100 ;

    Die Variable b ernhält nach der Zuwe isung b= a den Wert 400. Die nacht räglicheÄnderung des Wert s vo n a auf 100 be einflusst b nicht. Auch nach der Zmve isungb =a beze ichnen die Namen a und b untersch iedliche Variablen, deren ind ividuellbelegbare Weite an untersch iedliche n Speic heradressen verwaltet werden: DerWenzugriff üb er e ine Variable kann den w ert der anderen Variablen nicht bee tnfl us-sen . Konsequenz für d ie Programmieru ng iSI, dass Zuwe isu ngen zwische n Var iablenprimitiven Datentyps un prob lematisch sind: Nacht rägliche Wertänderungen eine r Va-riab len hat keinen Nebeneffekt für den Wert ande rer variablen .

    Durch de n Vergleic hsoperator == können Variable n primitive n Datentyps d irekt ve r-gliche n werden: a ==b ist e rfüllt, wenn a und b den gleichen 'lXb 1 tragen .

  • 161

    11.1.2 Primitive Datentypen als Methodenparameter

    11 R(:!erellzell

    Bei Methodenaufrufen könn en Variable n primitiven Datentyps an Merbod cnparame-rer übergebe n we rden. Dab ei wird ihr ak tueller Wen in den Merhoclenparamererkopiert - es findet ein e einfache wcnkopte stau , die a ls Call Gy Val ue bezeichn e twird. Somit können Veränderungen des übergebenen werts innerhalb der Methodeden Wen der Variablen außerhalb der Methode nicht beetntlussen.

    class CallByValue {

    public static void tuWas( int p )

    1/ p erhält bei Aufruf Wert 10

    p = 0; 1/ p hat nun Wert 0

    pub li c statie void main ( St ring [1 args ) (

    int w = 10 ;tuWas( w ) ;

    I O. wri t eln ( "We r t : " + W ) ; /1 Wert w immer noch 10

    Auch nach Aufruf der Methode tuW a s () mit dem Wen w behält d ie Variable w denursprüngliche n \Vert 10. Der Parameter p und die Variable w sind unabhängige Da-renbehälrer. Beim Methodenaufruf wird de r ' x'e rr von w in p kopiert. w ertä ndenm-gen in der Methode (p"" O) habe n teeinen Seilelleßekf au f dcn W ert der Variablen w.Vom dargestellten Verhallen primitiver Datentypen kann in j ava (im Gcg....nsarz ZUC++ ) nicht abg....w ichen w erd en.

    Leichte r Nachteil d iesc r intuitiven Arbeitsweise sind zusätzliche r Speiche rverbrauchun d Zeitbedarf durch das Kopie ren vo n Datenwerten lx- im Met hodenaufruf Deshalbwird der Catl By vatue in java für O bjekt e nicht angewandt .

    11.2 Objeklreferenzenj ede java-Variable die e in Objekt bezeichnet , stellt ein e Ref erenz au f d ieses O b j....ktda r. Heferenzen sind Zeiger (pointer ) auf die Spetcterad resse, ab der da s e igent licheO bj....kt im Hauprsp.... ich.... r abgcl....gr ist. Die B....dcunmg d .... r Referenz vcrdeutlich en wiran Obj ekten und O hj....krvariablen e ine r rudimentären Mirarbeite r-Klasse.

    class Mitarbeiter {

    public Str i ng name ; public double gehalt ;

    pub l i c Mi t a rbe i t e r ( St r i ng n , doub l e g) {

    name - n ; gehalt - g ;

    Es wcrd ....n Ohj....krvariablcn vom Typ Mita r beite r dckla ri....rt und initialisi....rt :

    c lass Referenzen {

  • 11 Referenzen

    public static void main( String[] args )

    Mi t a rbei t er ml ; 11 Deklaration der Objektvariablen

    Mitarbeiter m2;

    Mita rbeiter m3;

    // Erzeugen und Zuweisen de, konkreten Objekte :

    ml n•• Mitarbeiter ( " Mei e r " , 3000 ) ;

    m2 -new Mitarbeiter ( " Hub e r " , 4000 I ;m3 new Mitarbeiter ( " We i s s " , 5000 I ;

    165

    Grundsätzlich für das Verständnis des Begriff.. Referenz ist folgender Sachverhalt , de rin Abbildung 11.1 skizziclt wird:

    Die Objektvar-iablen (Rcf....-rcnzcn ) ml , m2 un d m3 sind nicht die Obje ktese lbst , sondern refercnzicrcn diese nur. Sit.' e n tha lten d it: spetcberadressen, abde nen d ie zugchörtgcn Objekte im Haup tspe teher zu finden s ind. Über dieSpeiche radresse k önn e n die Obje ktva riab le n auf "ihn:" Objekte lind de re n öf-fen tliche Eleme nte zugreifen . Jede O bjektreferenz re n eeist eindeutig auf e ineInsta nz ihrer Klasse .

    Die Klasse Mitarbei ter und daraus mittels new-O pcrator erzeugte Objekte bele-gen Speich erplatz. Bei den bloßen Deklaratio nen.

    Mita rbe iter ml ; Mita r bei ter m2 ; Mitarbeite r m3;

    werden nu r die Objekll'llriab/el/ (Referenzen ) ml, m2 lind m3 im Speicher angelegt.Sie enthalte n zu d iesem Zeitpunkt noch teetue gültige Speichera dresse . unter der Mit-arbeiter-Objekte zu finde n wären. Wir symbolisieren diesen Zustand durch d ieSchreibweise ml (*U) .

    Erst durch d ie lnitialisicrungcn mittels new-O pcrator und Konsrrukro raufruf

    ml new Mitarbeiter( "Me i e r " , 3000 ) ;

    m2 - new Mitarbeiter (

    m3 new Mitarbeiter (

    " Hube r" ,

    "We i s s " ,

    4000 ) ;

    5000 ) ;

    werden auch Objekte im Speicher angelegt. Der zuwets ungsopera ror = stellt die He-fcrcnz zwische n den Obje ktvariablen ml, m2, m3 und dem mit new belegten Spei -eherhereichen her. Die O bjek tvariab len rcfe rcnzicn-n d ie do rtigen Objekte bzw. zc i-gc n auf d iese : Sie enthalten nun gü ltige Spc k-hcradresscn, an dene n sich die zuge-wiesenen Objekte im Speicher be find en. Die zugewiesenen Speicheradressen habennur im laufenden JVM-I'rozess Gültigkeit. Beim nächsten Lauf des Programms kanndicscfbc Objektvar iab le ganz andere Adresswerte enthalten.

    In den Abbildungen verwenden wir wie üblich Pfeile, die von der Objektvariable nau f das rcfcrc nzic rtc Objekt ze igen un d tragen willkürlich gewählte symbo lische Ad-rosswert e ein, wie ml (4711) .

    Der l:up,rijJauf Objekte e rfo lgt also nicht di rekt , sondern indirekt via Referenz. An-sch aulieh kann das Verhäl tnis zwischen Objektvariablen (Referenzen) un d den Oh-

  • 166 11 R(:!erellzell

    jcktcn se lbst durch Analogien verdeutlicht werden: Die Eint räge des Inhaltsverz eich-nis e ine n Buches e n tha lten nicht die Kapitel selbst, aber sie ne nnen lind ke nn e n dieSeite nzahlen, ab de r die einze lnen Kapitel zu finde n sind . Die Einträg e rcfcrc nzicrcnihre Kap itel . Ein Straßenname samt Ha usnummer e nth ält nic ht sc hon das Hausselbst, ubc r die Informat ion , wo das Haus zu finden ist.

    m3 ne ... Mi t arbai.t9r ( " We i s s " , 5000) ;

    m2 o e w Mitarbeiter ( " Hu be r " , 40 0 0 );

    Illnitialisierung ;

    ml O Q W Mi t a rbeiter ( "Me i e r " , 3000) ;

    11 De klaration :

    Mitarbei ter m1 ;

    Mi ta r beite r m2;

    Mi t a r be i t e r m3 ;

    ml( ,lf## ) ---lm i # 1&"# ) --im 3(""N' ) --i

    Hea nRAM

    ~Stack

    1111( 2058 )

    m 2(Sl S6)

    (6988)m3

    \ dn.·, s.... n:

    IO.i2

    20SH

    5156

    Abb. 11.1 : Objektvariabl en (Referenzen) und refe renzie lle Obj ekte

    Durch die JVM er zeugte Objekte verfügen über eine e indeut ige Identität und we rdenmit e ine r ohj ekl -i l/ dit'iduellen Kelllll/ug ve rsehen. Somit sind alle Objekte übe r ihregesa mte Lebe nsdauer innerhalb des JV,\I-Prozess als un verwechselbare ldentiriltenun te rscheidbar. Die Objekt-Kennung wird sichtbar, wen n ma n den Inhalt e ine r Ob-je ktvariablen auf der Kon sole ausgibt:

    to . wr i te r n r "Re f e r en zen : " + mI + " " + m2 + " " + m3 ) ;Es werden drei unte rsch iedliche Kennungen au sgegebe n, da jede der drei Objcktva-rtablen ml, m2 und m3 ein eigenes, se parates Ob jekt rcfe rcnzicrr . Die Kenn ungensind bei jedem Programmlauf andere. Typischerweise werden sie aus der Speieber-adresse des ref erenrterteu Oly·ek fs be rechne t. Zusätzlich enrhälr die Ja va-Objek tkennun g auch den zuge hö rige n Klasse nn amen.

    Nur d ie laufende .J VM kennt d ie reale Spctchc radrcsse. an der s ich das Objekt bcftn-der. Som it ist d ie java-Objcktrcfcrenz ei ne log iscbe Ke nn ung, mit der die rea le Spei-chc radressicrung inn erhalb der .IVM assoz iie rt ist. Im Onrcrsch tcd zu Zeigern in denSprachen C und C++ e rlaubt Java leeinen dir ekten Zug riff auf d ie physischen Spei-che radresse n der O bjekte . Diese kö nnen nich t ausgegeben oder gar willkürlic h ver -ändert werden. Eine fehleranfällige "Zcigc rarithmctik" wie in C/ C++ wurde bewusstin Java ausgeschlossen. java-Rcfc rcnzc n e rlauben nur standardis ierte Operationen.

    Dass der Objekt-Zugriff in java mittels Refe renztypen o rganisiert iSI , e rweist sich alsVortei l bei der Übergabe von O bjek ten an Methodenpan..imcrc r ( s.u.) un d erlaubt d ieRealisanon dynam tscher Datenstrukturen (Kap itel HO.

    ln Abbildung 11.1 ist das sc he matische SJX!icbelbild für O bjek tva riab len (Referenzry-pcn) und die vo n ihnen rcfc renzic rrcn Objekt e angegeben. Die Objektvariab len ml ,

  • 11 Ref erenz en 16 7

    m2 lind m3 sind wie alle Variable nnamen symbo lische Bezeicbnc r für Speicher ze llenmit bestimmte r Spck-hcradrcsse . Der Inhalt diese r Ze llen ist jedoch seihs t wiederumjene andere Spe icheradresse ab der da s rc fercnzicrtc Objekt im Speic her e inget ragenist. Auch e ine primitive Variable wie int x = 4 ; ist ei n symbolischer Bczc lchncrfür eine n Speicherbereich. Der Inh alt dieses Bereichs ist jedoch keine and ere Spei-chcra dresse, so ndern e nth:i!t de n \'('en selbst (4 ) auf den d ie Variab le x zugreift.

    ln Java werde n Ob je kte s tets über O bjekrvntiablen via Referenz angespro-che n. Auf Variablen pr imitiven Datentyps wird dagege n stets d irekt zug cgrif-fen . Vo n dieser tec hnischen Vorgabe kann nicht abgewichen werden.

    An m erku n g: Alk java-Objcktvariablcn und primitiven mehrstauseben Variablenwerden auf de m Stack (Stapc lxpcicher)

  • 168 11 R(:!erellzell

    ma gc n unzegreifbare . Speicher versch wendende Stru ktur im Hau ptspe teh e r wi rd als"Spci chcrlcichc" oder Speiebe rieee (mcmory lcack) bezeichnet .

    In C++ ist das Progra mm seihst für das rechtzeitige Freigebe n solcher Spc khcrbcrci-ehe ve rantwortlich . Die spetcberreru-atmng in Cee-Programmcn kann lind mussd urch entspreche nde Sprach elemente (delcre-O pe raror, Destrukro rj ko ntrollie rt wer-den , Diese zu.

  • 16911 Ref erenz en

    Refere nzen s ind also auch in java eine spezielle At1 "Spcichcrkx.k''. ObsoleteHeferenzen sollten so mit sofort auf null geset zt werden.

    w enngleich in Java keine Dcstrukrcrcn programm ierbar sind , so gibt es doch ei nenschu-acben Ersatz dafür. Jede Klasse kann d ie spezielle Met hode:

    public vo Ld finalize ( ) { /» 'j }

    impleme ntie ren . Diese wird d irekt vo r de m un wiederbring lichen Lö schen des O h-jckts durch d ie Garbege Co llccüon einmal aufge ru fen und darf bclichtgcs Codingenthalten. Typischerweise sollte es sich dabei nur um letzte abschließende "Auf-räumarbcitcn" han del n (Freigebe n von Betriebsmitte ln wie Nerzwe rk- oder Date n-bankverbindungcn, Lo g-Einträge sc hreibe n c tc.) .

    \,\' ir erweitern un se re Klas se , um de r Garbagc Collccnon beim Arbeire n "zuz use he n"-

    c l ass M~tarbeiter I

    Mitarbeiter( String n , double g)

    public

    public

    String name ; public double gehalt ;

    name: n ; qehe l t ... g ;

    publ ie vo~d f~nal~ze()

    10 . wri t e In ( "Ob j e k t + name + " zerstört " ) ;

    Mitarbeiter m2 -new Mitarbeiter ( " Hub e r " ,Mi tarbeiter m3 new Mitarbeiter( "We i s s" ,

    m1 = nu l l ; m2 = nu l l ; m3 = nul l ;

    Sy stem . g e () ; 11 Aufruf Ge

    elas s Referenzen {

    public static void

    Mita rbeiter ml

    Obj ekt Weiss zerstört

    Objekt Huber zerstört

    Obiekt Meie r zer s t ört

    main ( String [ 1 args ) 1

    new Mitarbeiter( "Me i e r " ,

    - Konsole -

    3000 ) ;

    4000 ) ;

    5000 ) ;

    Durch Aufruf der statischen Methode System . gc () wird der Garbuge Colk-ction"nahe gelegt" 6 1ig zu werden.

    Die Methode fina li ze () sollte sparsam und mit Bedacht eingesetzt werden. Fürden Entwic kle r isl n iehl konrrollicr- und vorhcrschbar, w ann gc nau die Garbagt.' Col-leenon tätig wird. Somit ist der gt.'nalle Aufrufzenpun kt vo n finalize () relativ z

  • 170 11 R(:!erellzell

    fo lgende n Programmteilen aus Entwicklersicht n icht dererminiert. De r Einsatz derMethode kann zudem die Performanz bccmträchngcn [BL004].

    In Abbildung 11.2 ist de r typische O bjek t-Lebenszyklus als Zustandsdiagramm(WvIL) eingerrage n. Das Zusta nds diagramm verzeic hnet die Abfolge der Zustände.die O bjekte innerhalb der Anwendu ng durchbuten lind vermerkt Aktivitäte n, d ie ei-ne XUSlälldsäJldel7/11l{ (Übergan g von einem Zustand in einen anderen ) bewirken.

    11 .2.2 Zuweisungen zwischen Referenztypen

    Eine deklarierte O bjck rvartablc kan n mittels new- O perato r lind Konstrukte raufrufinit ialisicrt lind ihr ein neu e rstelltes Objekt zuge w iesen we rde n. Alle rdings kann e i-ne r de klarierten Objektvariable n auch e ine bereits in itialis ic rt c Objektvariable desgleichen Klassentyps zug ewiesen werden.

    Mitarbeiter ml new Mitarbeiter( "Me i e r ", 3000 ) ;

    Mi t arbeite r m4 = m1 ; // Zuweisung einer Objektvariablen

    lm Gegensatz zu primitive n Datentypen wird in diesem Fall leetueKopie dcs Objektsvon ml erzeugt lind m4 zugewiesen. Vielmehr wird /1111' die Referenz selbst lKJpie11,d.h . die Speicheradresse dcs Objekts. Som it enthalten als Ergebnis der Zuweis ungm4=ml nun betete Objektvariablen dieseihe Speicheradresse. d.h . sk- rcfcrcnzicrcnein /ll/d dasselbe Objekt.

    Zuw eisunge n zwische n Ob jektva r -iab len (Rcferenzrypcn) bewirkt eineKopie der Referen zen. Som it zeigen (rcfcrenztcrcn) mehre re Objektvariab-len auf dasselbe O bjekt un d kö nnen auf dieses verändernd zugretten.

    ln Abbildung 11.3 ist e rsichtlich, dass durch die Zuweis ungen m2=ml und m3=mlschließlich alle Objektvariable n mit demselben Mirarbe iterobjekt im Speicher arbei -ten, d .h. auf dasselbe O bjekt verwe isen . Offensichtlich kann auch einer bereits iniria-hsicr ten Objektvariablen eine ne ue Referenz zugewiesen werde n. Auf diese 'x'etsesind die Objek te, auf die m2 und m3 ursprün glich zeig ten , nun mehr verwaist. Als un -referenzierte Java -Speic herleic hen werden sie von de r Garbuge Collection automa-tisch entso rgt. (In C++ wäre dadurch ein Speicherleck cntstan den.)

    Eine Manipulation des Obj ekts über eine der d rei Objektvaria ble n ist somit au ch fürdie anderen wirksam:

    m1 . g eha 1 t -2000 ;m2. geha1 t = 1 0 000 ; 11 Verändert Objekt zustand über Variable m2

    IO . writeln( "mI sagt : + ml .gehalt I , 11 Liefert : 10000

    IO .writeln( "m3 sagt : + m3 .gehalt I , 11 Liefert : 10000

    Die über m2 vo rgenommene Gehaltsä nderung ist über ml lind m3 abfragbar. da alled rei O bjek tvariab len au f ein un d dasselbe Objekt verweisen. Durch Ausgabe der Ob-jekll~ellllJ/Jlg vor und nach Zuweisung der O bjek tvar iablen könne n die Referenzver-hälmisse demonstriert we rde n:

    c lass Referen ze n {

    public statie void ma Ln ( String l l a rgs ) {

  • 11 Referenzen 171

    Mitarbeiter m1 new Mitarbeiter( "Me i e r " , 3000"Mita rbeiter m2 new Mitarbeiter( " Hub e r " , 4000 I ,

    Mitarbeiter m3 n ew Mitarbeiter( "We i s s " , 5000 I ,

    IO . wr iteln( "Re f: .. , m1 , .. .. , m2 , .. " , m3 I ,m2 = m1 ; m3 = ml ; II Zuweisung dee Referenzen

    IO . wri teln( "Re f : .. , m1 , .. " , m2 , .. " , m3"

    - Konso l e -

    Ref : Mitarbeite r @3 1 79c 3 Mitarbeite r @31 0d 42 Mita rbe iter@Sd 87b 2

    Ref : Mitarbeiter@ 31 79c 3 Mitarbeiter@31 7 9c 3 Mitarbeiter@3 1 7 9c 3

    Mitarbeiter ml , ro2 , m3 ;

    ml new Mi t al'bei ter ( "Me i e r " , 3000) ;

    205H

    GC gibtSpeicher

    H frei

    RA,\I ;\ d rcs ",-" n:

    m2 = ml ;

    m3 = ml ;

    new Mi t arbeiter ( " Hub e r " , 4000) ;

    n e w Mi tar bei ter ( " We i s s " , 5000) ;

    // Zuweisung der Referenz:

    m2

    m3

    Abh. 11.3: Zuweisungen zwischen Objektvariablen - Ko pie der Referen z

    Vor Zuweisung der Objektvariablen e rhält man dre i unterschied liche Objektkennun-gcn . Nac-h Zuweisung der Objektvariab len ml, sind die Kennungen identisch , da nunalle Objektvariablen das ursprün glich nur ml zugewiesene Objekt rcfc rcnzicrcn.

    Da drei Objektvar iablen dasselbe Objekt refcrcnztcren. bleibt das Objekt im Spei -cher erhalten, auch wenn e in oder zwei der Objektvariablen auf null gcscrzr wer-den. Die ve rbk-ibende Referenz hiilr das Objekt am Leben. Erst nachdem auch d ieletzte Referenz entfe rnt wurde, wird die Gar hage Collcction tätig Lind zerstört dasnunmehr un rcfc rcnzic rtc Objekt:

    ml = nu11 ; m2 = nu11 ;

    // Noch über m3 referenziert und zugreifbar :

    IO .writeln( " Na me - " + m3 .name ) ;

    m3 = null ; 11 Erst jetzt kann Ge tätig werden

    \Xli;: auch bei Zuweisunge n zwischen primitiven Datentypen müssen die zugewiese-nen O bjektv ariab len typk ompatibel sein :

  • 172 11 R(:!erellzell

    Voraussetzung für die z uwetsba rketr vo n Obje ktvariab le n ist d ie Tvpkom-panbihtät der zugehörigen Klassen. Nur die Konstan te null kann jeder Oh-[ekrvariablen zugewiesen werden.

    Die zugewiesenen Objek tvariablen müssen vom 7) '1' derselben Klasse (hier: Mi t ar -b e i ter ) sei n. (Im Kontext der Vererbung werden wir den Begriff de r Typkompari-bihtär von Objektvariablen jedoch e ntsc heide nd vc rallgcmcincm.) Eine blogc Struk-turäquivalcnz der zugrunde liegenden Klasse n ist nicht ausreich end . Nicht rvpgc-rechte Zuweisungen zwischen Objektva riablen füh ren zu einem Compilerfehler.

    class Mit arbei t er pub l i c String name; pub l i c d ouble gehal t ;

    c l ass Ange stellte r I pub l ic St r ing name ; public d ouble gehalt ;

    class Zuweis ung I

    pub lic static void main ( String [1 args ) I

    Mitarbeiter ml = ne w Mitarbeiter( ) ;

    ml . name '" "Me i e r " ;

    Ange s t e l l t e r &1 '" m1;

    Mi t a rbeiter m2 = m1 ;

    ml . gehalt = 3000 ;// Fehler: Unterschiedlicher Typ!

    // OK: Gleicher Typ!

    Für die Instanzii emng vo n Objek tvar iablen giht es nun mehr zwei i\lögJichkei!e n:

    1. Objektvar tnblcn kön ne n instanzfiert werden durch den n c w -Opcrator undKonslruktoraufruf. Dadurch wird ein nenes Objekt im Speic he r angelegtund durch die Objektvar iable rcfcrcnz icrt:

    Mi tarbei ter m1 = ne w Mitarbeiter ( "Mei e r " , 3000 ) ;

    2. Obje ktvariable n k önne n instanz fiert werden durch Zuweisung e in e r b e -reits initiaJisicrtcn Objektvarfablen . Es wird kill ncucs Objekt im Spei -cher angelegt , sondern d ie Refere nz de r zugewiesene n Objektvariablen ko-picrt . Die Objektvariab len rcfcrcnzic n-n nun ge meinsam das Objekt de r zu-gewiese ne n Objektvariablen.

    Mitarbei ter m2 = m1 ;

    11.2.3 Vergleiche zwischen Objektvariablen

    Objektva riablen (Rcferenzrypen} kö nnen mit den Vergleichsoperatoren ='" und ! '"auf Gleichheit und Ungleichbett geprüft werden. Jedoch wird dabei nicht der Zu-stand der rcfcrcnzicrtcn Objek te (interne Artnbuticrung) vergl ichen, so nde rn der ln-ha lt der Objek,,·ariablen, d. h. die darin gespeich erte R4e1"(:'lIz.

    Beim Vergle ich zwe ter Objektvariablen mittels des v erglctchsopcrators --werden die Refe ren ze n auf d ie Objekte ve rglichen. Es wird festgestel lt, obbeide Objek tvariablen dasselbe Objekt rcfcrcnzlercn.

  • 11 Ref erenz en 173

    Die Vergleichso peration liefen so mit true, wenn beide Objektvariablen au f dassel -be Objek t verweisen (Ohjekfide ll tifiiO, andernfalls false - auch we nn d ie Attribut-bclcgung der beiden Objekte identisch ist:

    class M~tarbeiter I public String name ; public double gehalt ; )

    class Vergleich (

    pu blie statie void main( String[] args

    Mita rbeiter ml = new Mitarbeiter() ;

    ml . name = "Mei e r " ; ml.gehalt = 3000 ;

    Mi tarbeiter m2 = new Mitarbeiter() ;

    m2 . name = "Mei e r " ;

    Mitarbeiter m3 = ml ;m2.gehalt = 3000;

    test = ( m3 == ml ) ;

    boolean test = ml==m2 ); // liefert false !

    11 liefert true !

    Die Objek tvar iab len ml und m2 rcfercnzicre n unt erschiedli che Objekte . Trotz Wert-gle ichhei t der Amhutc (ide ntische r Objcktzuxtand ) liefe rt ihr Vergle ich false. Da-gegen rcfcrcnzicn-n ml, und m3 dasselbe Objekt, so dass der vergleich true ergibt.

    Möchte man e ine n wertecergkrich de r gespeicherten Attrihntc zwische n verschiede-nen Objekten durchführen (Test auf \'Vc/1üquil'ufc/l z ), so ist dazu eine etassenspe z i-f ische Vergleichsmettode zu impleme ntieren , d ie d ie relevanten Anrtbutwcrt c (Zu-stand) der Objekte vergleich t. \'\'as relevant ist, muss innerhalb des semantischeuKon textes der Anwen dung festge legt werden. Die Vergleichsmethode kan n eine Mc-thodc de r Klasse selbst se in ode r separat imple mentiert werden.

    In folgendem Be ispiel werde n in Objek ten de r Klasse Zeit Zeitpunkte au f Sek un-dengenauigkeit verwaltet. Als identisch betrachten wir jedoch zwe i Zeitpu nkte be-reits, wenn sie nur in der Stunde n- und Minutenangabe übere instimmen. Dies wirddu rch e ine statische Vergleichsmethode umgeset zt:

    class Zeit I

    public int stunde , publ ic int minute ; public int sekunde ,

    public Zeit( int std , int min , i nt sek )

    stunde = std ; minute = min ; se kunde sek ;

    public static b oo l e a n istGleich ( Zeit z l , Zeit z2 l

    return (z l . s t und e == z2.stunde ) && (z l . mi nu t e == z2.minute );

    class Ve r g l e i c h (

    public static void main( String[ ] args )

  • 171

    Zeit t l

    Zeit t2

    new ze t r t 11 , 45 , 26 ) ;

    new ze t t : 11 , 45 , 56 ) ;

    11 R(:!erellzell

    11.2.4

    boolean test ~ Zei t . i s t Gl e i ch( t l , t 2 ) ;

    Kopieren von Objekten

    1/ liefert true

    Dirc-ktc Zuweisung zwcicr Objektvariablen bewirkt, dass die se dasseihe O bjekt rcfc-renzieren. Um ein Objekt z u 4>Ol'ierell (clonen ), muss ein nenes Objekl der Klasse er-zCII,gf lind desse n Attribute mit den Attributwerten des Ursprungsobjekts gefüllt wer-den. Ziel ist d ie Herste llun g zwcic r vö llig uoa hh:ingigcr wertidentischer Objekte imgleichen Zustand. In j ava ist dafür ein Ablauf auf Basis der Methode clone () vor-gesehen, Die zugehörigen Mechanismen sind jedoch teilweise et was komplizie rt, sodass wir diese als ergänzendes Material auf der Buch-\X'ehseite da rgestellt haben.

    Die d irekte Verwendung von Konstruktu ren (auch in mehrfach überladener Fo rm)zur Objek terzeugung ist uns mitt lerweile ve rtraut. Jedoch existie ren noch stärke r ge-kapseire Kontexte, in denen Konstruktu ren verwe ndet werden kö nnen , um d ie ei-gent liche Objekte rzeugu ng ge naller zu kontrollie ren.

    Sogena nn te Kopter-Konstmletoren (Copy Co nstructor) sind spezielle Konstrukron..-neiner Klasse . Deren Parameter ist vom Typ der Klasse se lbst. Somit kann die Rcfc-rcnz auf bereits erzeugte Objekte übergebe n werden. Die privaten Attr ibute desübergebene n Objekts sind dabei zugre ffbar. da dieses vom Typ dersel be n Klasse ist.

    lm Beispiel sind alle Attribute prtmtttre Datentypen. Der Konstrukro r erhält ei n be-reits initialisie rtcs Objekt und initialisicrt mit desse n zustandswerten das neu zue rste llende Obj ekt. Dieses ist somit e ine exakte Ko pie des übergebenen O bjekts:

    c lass Konto I

    private int kontoNr ; private double saldo ;

    publ i c Konto ( Ko n t o k ) I // Kopier-Konstruktor

    this( k . kont oNr , k .sa l do ) ;

    public Konto( i n t kn , double sd ) t

    kontoNr - kn r saldo - sd ;

    Eine Aufruf des Kopicr- Konstruktors härte fo lgende Gesta[t:

    Konto origina l ~ new Konto( 4711 , 2000 .0 ) ;

    Konto kop ie = new Konto( o r igi na l ) ;

    Dieses einfache Vo rgehen ist jedoch nur bei Attribute n primirir en Datentyps angc-bracht. Ernhält eine Klasse Attrib ute vom Typ e ine r anderen Klasse (Assoziation ), sosind auch dies Objektreferenzen. Durch ein Attribut dat vo m Typ der Klasse Datumver fügt ein Konto-O hjekt nun über e ine interne Tiefe nstruk tur, die bei m Kopi eren

  • 11 Ref erenz en 175

    be rücksichtigt we rde n muss . Eine di re kte Zu weisung dieses Attributs würde nur eineflache Kopie csbattou.copy) erzeuge n:

    class Datum public int tg ; public iot mon ; public int jr ; }

    class Konto

    private int kontoNr ; private double saldo ; private Datum dat ;

    public Konto( Konto k ) ( 1/ Kopier-Konstruktor

    t his( k . kon t oNr , k . sa l do , k .dat ) ;

    public Konto( int ko , double sd , Datum d )

    kontoNr - kn ; sa ldo - 3d :

    dat - d ; 1/ nur flache Kopie der Datum-Referenz

    Hier rcfcrcnztcrt das Attrib ut dat vo n Ursprungsobjekt lind Kop ie dasselbe Datum-Obje kt, so dass teetue völlig un abhängigen Obj ekte erzeugt wurden: Jedes der O b-jekte besitzt nun als Att r ib ut eine Referenz auf dasselbe Datum-O bjekt.

    Abhilfe scha fft eine I ief e Kop ie ( dee!, c()!~}') , in dc r auch d ie Attribute assoziiertc r Oh-jektc einzeln kopiert werden (sofern es sich um primitive Datentype n und nichtselbst um Objektreferenzen handel t>:

    publ~c Konto( Konto k ) ( /1 Kopier-Konstruktor

    this( k .kon t oNr , k . s a l do , k .dat ) ;

    public Konto( i nt kn , double sd , Datum d )

    kon t oNr '" kn ; saldo"" sd ;

    11 Tiefe Kopie der Datum-Referenz :

    d a t . t g = d .tg ; dat .mon = d .mon ; dat .jr = d .jr ;

    Nur durch e ine liefe Ohjekl!..«)!)ie entsteht e ine echte Kop ie als völlig unab hän -g iges Obje kt, das nicht über Referenzen an das Llrsprungsobjekt ge ko ppelt ist.

    Neben Ko pier-Konsrrukroren sind noch weitere Var iante n verbre ite t. Ein Konrersi -ons-Konssmtaor erstellt e in ncucs Objekt seiner Klasse unter Verwendung vo n w er-rcn und Zust änden ein er Refe renz eines an deren Klassentyps. Auf d iese \,\'d se kön -nen d ie Daten eines be rei ts exis tierende n Objektes verwe nde t werden, um ein Ob-jekt anderen Typs zu Inmaltstercn - ode r das interne Date nfo rmat dabei zu verttn-de m . Scho n im vo rangegange ne n Beispiel d ienten Referenzen der Klasse Datum zurlnitlalisicrung eines Kon t o-Objekts.

    publ~c Konto( int kn , double sd , Datum d ) I 11 " Konv e r s i on"

    kon t oNr '" kn ;

    dat .tg "" d .tg ;

    saldo'" 0 .0 ;

    dat .mon '" d .mon ; dat .jr d . jr ;

  • 176 11 Rt.:!erellzell

    Eine Kapseiung aller Detai ls der Objek terzeugung kann in statischen Fo CfOJ)'-J1clhod c l / erfolgen. In d iesen wird das Objek t erstellt, sei n Initialzustand festgelegtund die Referen z an den Aufrufer zurückgegebe n. Die eige ntliche n Kon struktorcnder Klasse könnt en und sollten in diesem Fall private sei n, um ein Unterlaufen desFactory-Mcchan lsmus durch Verw ender der Klasse zu ve rhindern .

    c~ass Konto (

    private int kontoNr ; private double saldo ; pr ivate Datum dat ;

    I! Statische ractory :

    public statie Konto createKonto ( double sd ) I

    Konto k ~ new Kanto( 3d };

    k . kontoNr - getKontoNummer() ;

    return k;

    k .dat - getDatum() ;

    I

    11 Keine direkte öffentliche Objekterzeugung!

    private Konto( double 3d ) { saldo - 3d; )

    11 private Generatoren für Datum und Kontonummer :private statie Datum getDatum() I /. ./

    private s ta t Lc Ln t getKontoNurnmer() I /. ./

    Es können mehrere versch iedene Facto rics unterschiedlicher Sem antik ex istieren -sogar mit identischen Parametert ypen aber un tersch iedlichem Methodennamen.Nachrräglk-h sind beliebige weitere Varianten beliebiger I'aramctrisk-r ung e rgänzbar.Dies wä re durch über ladene Konsrmkron-n nicht realisierbar. Statische Pactorics sindKon struk toron oft übe rlege n und ve rbe rgen d ie Details lind Komplexität de r Objekt-erstellung vor de m Verwe nde r. Somit spricht einiges dafü r, Konstrukte ren doch ehe rals private Details ihrer Klasse anzusehen [ESSOS].

    11.2.5 Finale Objektvariablen

    Objektvariable n kön nen als final deklariert werden. Bei einfache n Datentype nbedeute te die Deklaration final , dass es sich um eine Konstante ha nde lt, de renWelt nicht mehr ve rändert we rde n darf. Objektva riable n jedoch sind Referenzen aufObjekte , nicht die Objekte selbst. Ihre Kennzeichnung als final (nicht veränder-ba r) bedeutet , da ss ihre Rcferenr nicht rcrände rt we rden da rf. Somit darf einer fina-lcn Objektvariable kein anderes Ohjel!l zugeu-tesen we rde n . Konstant ist d ie so mitd ie Rd e rl'nz, nicht de r Zllst:md (Altrihllthdegung ) des rd e renz ie r1en Objekls.

    Eine finale Objektvari ab le muss immer dasselbe Objek t referc nzie ren. Ihrdarf kein Verweis auf ein ande res Objekt zugewiesen werden.

    Dagegen dürfen d ie Attributwerte (Zustan d) des final refercnztcrtcn Objekts d urch-aus ve rändert werde n. Zur Demonstration verwende n wir obige Klasse Zeit:

    class Vergleich I

    public s t a t Lc vo i.d rna i.n ( String l l a rgs ) I

  • 11 Referenzen

    f inal Zeit tl = new Zeit ( 11 , 45 , 26 ) :

    Ze it t2 "" new Zeit ( 16, 22 , 56 ) ;

    // Erlaubt : Änderung Attributwerte (Zustand) des Objekts

    tl. s tunde = 15 ;

    // Compile-Fehler:

    177

    tl t2 ;

    t l = null ;/1 Nicht erlaubt : Änderung der Referenz

    11 Nicht erlaubt : Zuweisung null

    Die finale Objektvaria ble tl referenzlerr ein Objekt, desse n Anrtburwerte trotz derf Lna L löe klarat ion von tl verä ndert werden dürfe n. Jedoch darf die finale Objekt-variable t l kein anderes Objekt referenzieren . Der Versuch, sie durch Zuweisungt l =t2 auf das an dere Zeit-Objekt zu verweisen oder d urch Zuweisung von nulld ie Referenz zu entfe rnen, liefert eine n Compilerfehler.

    11.2.6 5elbstverweis mittels this -Referenz

    Innerhalb des Klasseneod ings kann explizit auf d ie e igenen Attribute und Methodendes aktuellen Objekts zugegriffen werden . Dazu dient d ie vordefinierte finak- ü)t.h i.e-Rcfc renz: (liest.' isl ein Alül.I'(StdlveI1reternalllc) für das Objekt sdbsl in seinenMerboden-lmplemenrterungeo . Mittels this bezieht sich das Objekt auf sich selbst.Ein expliziter Attribut- und Methodenzugriff geschieht mittels:

    this .Attributname bzw. this .Methodenname ()

    Mittels this verfügt ein Objekt über eine ucfcrenz aufsich seihst, d ie innerhalb desCodings seiner Klasse e ingesetzt werde n kann . Die t n t s-Refc rcnz iSI in stat tsehe nMethoden nicht verfügbar, da sich diese nicht auf ein spezielles Objekt beziehe n.

    Eine einfache Anwendung ist die verwendurig vo n this zur Aufläsu /lg /VII Sa-mens-Zueideutigeeiten bei Paramete rübergaben an Methode n:

    c l ass Mitarbeiter I

    private String name; private d oub l e gehalt ;

    p ublic Mitarbeiter( St r i ng name , d ouble gehalt ) {

    t his . name = name; thi s .gehalt = ge h a l t ;

    // name name ; gehalt gehalt ; // wirkungslos!

    t h is . setName ( "Dummy " ) ;

    p ublic void setName( String nm ) {

    name = nm. ;

    this .name = run;

    // hier sind die Namen eindeutig

    // syntaktisch erlaubt , aber unnötig

  • 178 Jl R(:!erellzell

    Die Paramet ernamen de r Konstruktormcthodc lauten gleich wie die Attributnamender Klasse. Durch die t h i s -Sclbstrcfcrcn z in this . name wird für den Compilerdeutlich , dass mit this . name das Attribut name des erzeug ten Objekts angespro-che n wird, während d ie zugewiesen e Variab le name de r gleich namige Mcthodcnpa-ramcrcr ist. \X' ürd e man stattdessen name=name codieren, so würde de r Param eterals lo kale v ariable d;IS Attribut ve rdec ken und sich selbst zugewiesen we rde n . Derdem Konsrruk tor übergebene Wert würde nicht im Attribut name "anko mmen".

    Der exp lizite Selbstbezug mittels this da rf in e ine r Klasse übe rall verwende t wer-den , wo in ihren Method en auf Attribute oder Methoden de r Klasse zugegriffenwird . Die explizite Selbstreferenz kann entfallen, wcnn > wie in de r Methode set -Name () - gar kein Namensko nflikt auftr itt .

    Mittels this können auch Attribute vo n gleichnamigen lok alen Methodenvariablenun tersch ieden werde n. Durch die t.h i s -Sclbstrcfcrcnz wird stets das bet reffe nde AII -ribnt des Objekts bezeichnet :

    c1ass M~tarba~ter (

    pr~vate Str~ng name = "Mei e r " ; I/ Attribut

    pub lic void printName()

    String name = "Dummy" ; 11 Gleichnamige lokale Variable

    rO .writeln ( name ) ; I/ Lokaler Variablenwert " Dummy"

    ro.wr i t e r n j this.name ) ; 11 Attributwert "Me i e r"

    Die lokale Variable name der Methode rerdeclet das Attribut neme. Dieses wirddurch this . name explizit angesprochen und die Verdeckung aufgehoben.

    Die t h i s-Sclbsrrcfcrcnz liefert e inen Verweis auf ihr zuge hö riges Objekt. Als sinn-volle Verwe ndung der Selbst referenz können Methoden t hi s zurücklicfcrn, um aufe inem Objekt mehrere solche Methoden nacheinander ve rkettet aufrufen zu kö nnen- wie in folgendem (e twas k ünsrhchenj Beispiel . Durch den Rückgab ewert thisübergibt ein Objekt die Referenz au f sich selbst bei Aufruf der Methode setGe-ha I t () und setName () :

    c1ass M~tarba~ter (

    private String name ; private double gehalt ;

    public Mitarbe~ter setName( String n )

    name = n ; return this ;

    pub lic Mitarbe~ter setGehalt ( doub le g )

    gehalt = g ; return th~s ;

    public void speichereDaten ( ) r- ... ~ /

  • 11 Ref erenzen 179

    c lass Demo I

    public statie void main( String [] args ) {

    Mitarbeiter m ~ new Mitarbeiter() :

    m. setName ( "Meier" l . setGehal t ( 3000 .0 l . speichereDaten () ;

    Di e t h i s-Rcfcrcnz ist fina l, d.h. ihr kann nicht d ie Referenz auf ein anderes Ob-jekt zugewiese n werden (\V;IS sinnlos wä re ), aber auch e in "Selbstmord" des Objek tsdurch d ie Zuweisung this=null wie in der Methode.

    public void suiz id() { this - null ; I // Fehler: this ist final!

    wird vo m Compiler nicht akzeptier t.

    .1I,1an verwechse le d ie this-R{:lereJlz nicht mit dem Aufruf e ines Konstruktc rs d urcheine n anderen Konstrukror der Klasse (Kapitel 10) mitte ls der stetboäe this ().

    11 .2.7 Anonyme Objekle

    Ein mittels new-O pc rator und Konsrru kro raufruf e rze ugtes Ob je kt wird ei ne r Ob] ....kt-variable n zug....wie sen un d durch diese Refe ren z im Spcich cr g....halte n. ehcr dcnAUIIIL'JI der O bjektreferen z ist da s Objekt während des Programmlauts ansprecbbar.

    Allerdings k önn en Objekte ancb ohne ei,WI/{!1I Namen (rcfcrcnzk-rcndc Objck rvari-ablc) erzeugt und in e ine r ei nz ige n Anw eisun gsfolge direk t ge nutzt werden:

    c lass Mitarbeiter I

    pr ivate String name ;

    p ubLi c Mitarbeiter( String n ) I name = n ; }

    public void info() { I O. wr i t eln ( " Na me: " + name + " " ); I

    class Anonym {

    publ ic static void main( String [ 1 args )

    new Mitarbeiter ( "Meier" ) . i n fo l); /1 Anonymes Objekt

    Man sp richt von einem a ll Ollym(;'n Ohjekt , J a es kein en eigene n Namen (O bjcktrefc-renz) besitzt: D:IS Obj ekt wird im Speicher ang elegt und die Methode info () dire istdarauf aufgerufen. Danach ist das Obj ekt sogleich ein Fall für die Carbagc Collccti-on, da es IYm ee iner Ohj ekll'a r ialJlell reje rellz ier t wird. Somit kan n es auch IIW" inder erzeuge nden Anw eisun g verwendet werden, ist also eine Art "Etnwcgobjckt''.Soll e in Obje kt wirkli ch nur e in einz iges Mal verwendet werden , spart man au f diese\Veise das Anlegen ei ne r se para ten Objektreferenz.

    11.3 Objekte als MethodenparameterEbe nso wie primitive Datentypen können auch O bjekrvadablen als Metbodenpa ra-meter verwen det werden. Grundsdtzlicher Unterschied zur Übergabe primitiver Da-

  • 180 Jl Rc:!erellz ell

    rentypen (Callüyvalue-Scmanttk) ist jedoch : Es wird eeine Kop ie des be treffendenObjekts erstellt und an d ie Methode übergeben , so nde rn die Ref erenz auf das Objektwird W I den Method enparameter iibe1]!,ebell. Somit refcrenzicrt der Methodenpara-meter da s Objekt , d. h. ken nt dessen Speicherort . In de r Methode wird somit nich tmit e iner Kop ie des Objekts ge arbe itet, sondern alle Manipulatione n ge sche hen di-rekt mit dem "Original-Objekt". Fo lgendes Beis piel verde utlich t die Vorgänge.

    c lass Mitarbeiter { public String name ; p ublic double geha l t ;

    c lass CallByRef {

    public static void zuschlag( Mi t a r bei t e r m l {

    m.gehalt = m.gehalt + 500 ; 11 Zugriff über Referenz

    publie statie void main ( String l l args ) I

    Mitarbeite r Meier ~ ne w Mitarbei te r ( ) ;

    Meier .name "" " Me i e r " ; Meier .gehalt "" 250 0 ;

    IO .writeln( " Ge h a l t wa r : " + Meier .gehalt ) ;

    zuschlag( Meier l ;

    IO .writeln( " Ge h a l t ist nu n : " + Meier .gehalt ) ;

    - Ko ns o l e -

    Geha l t war : 2500

    Gehalt is t nun : 3000

    Das d urch d ie Objektvar iable Meier refcrcnzie rtc Mitarbei t e r -Objckt ist nachdem Methodenaufruf in einem a l/deren Zustand als zuvor. Durch Übergabe der Re-ferenz Meier an de n Methodenparame ter m wi rd im Methodeneodi ngs über die lo-kale Refere nz m auf das Objek t zugegriffe n un d der Atrriburwcrt gehalt ver ände r.Die w crtändc rung ist au ch nach Abarbci tung der Methode weiterhin sichtbar. Wäh-rend des gesamten Programmlaufs exis tiert nur ctn Mi t e rbeite r-Objekt im Spei-che r. Dieses wird vo n der Objektvar iablen Me i e r refcrcnzicrt - jedoch n-ährend desMethodenaufrufs auch von de r lok alen Parameterrefere nz m. Alk Mani pulationen er-folgten somit stets an ein und de mse lbe n Objekt.

    Methoden können Objekrvuriablcn als Parameter besitzen. Beim Methoden-aufruf wird eine Referenz auf da s e ntspreche nde Objekt an die Parameter derMethode übergeben. Diese Art des Methodenaufrufs wird als Call Hy Hefe-rence bezeichnet. Zustandsänderungen an dem Objekt Innerhalb des Metbo-dencodmgs sind auch nac h dem Methodenaufruf wirksam.

    Ahbild ung 11.4 stellt d ie Objektreferenzen während des Methodenaufrufs dar: Aufdas Mitarbeiter-Objekt ze igt die Objektvariable Meier und auch die metheden-lokal e Objektvariable m, übe r die der Gehaltswert ve rändert wird . Die loka le Rcfe-

  • 11 Referenzen IR I

    renz m existie rt nur wäh rend des Methodeaufrufs. Das Objekt selbst bleibt jedoch imSpc k-hcr solange e s vo n e iner Obje ktvariablen rcf....-rcnz icrt wird .

    class CallByRef I

    205M

    Hl.i l

    IIc a .\ dn: s.';c n:

    RAM

    Stack

    M eier

    Objek t

    Mitarbeiter-

    ... void zuschlag: Mitarbeite r m ) 1...

    ... void rnain f ... ) 1 / .."

    Mirarbeiter Meier / /

    ;;"' hlo

  • 182 Jl Rt.:!erellzell

    gelöscht. Som it mu ss dlc Objektreferenz von einer ko rrekt typisierten Objckrva riab-lcn elltgegellgellommen werden, damit das durch die Methode erzeugte Objekt überdiese Referenz erhalten wird. Andernfalls wü rde es un rcfc rcnxicrt de r Garbuge

  • 11 Ref erenzen 183

    • Me thoden könne n a ls Paramete r referenz tene Objekte in ihrem Zustand reran-dem . Zugreffbare Attribute kön nen man ipuliert, d ie öffentliche n Objcktmcrho-den dazu verwen det werden. Nach de m Meth odenaufruf befi ndet sich das be-treffend e O bjekt in einem anderen Zustand als zuvo r. O hne dass d ie Methodeeinen Rückgabewert bes itze n mü sste , hin te rlässt sie doch e ine Wirk ung in demübe rgebene n Objekt.

    Rcfercnzicrtc Obj ekte können dabei als beliebig komplexe Daten- abe r ebe n auchMethodenbehälter d iene n. Als Para meter ode r Rückgabcwcnc vo n Methoden dien ensk zur Übergabe oder Rück gabe nicht nur belie big komplexer Datenme nge n son-de m auch von Punktionallrät. \'('enn wir eine r Methode beim Aufruf d ie Referen z aufein Objekt übergeben , so hat die Methode Zugriff auf desse n Attribute (Date n) aberebe n auch auf dessen öffe ntliche Methoden (Punkrion alität) .

    Wir gewinnen da durch e ine verallge meine rte Sicht auf dlc Wirkun g von Meth odenlind ihre Schnittstelle: Mittels Objektreferenzen adressiert d ie Mcthodcnschnirt srcllcnicht nur Daten so nde rn auch Funknonalhär :

    In folgen de m Beisp iel füh rt e ine Methode e ine Transaktion durch, die den Zustandzweier Objekte kon siste nt ve rändert.

    c1ass Ko n t o (

    private int kontoNr : private double kontoStand :

    public Konto ( int nr , double betrag)

    kontoNr - nr ; kontoStand - betrag ;

    public void a bheben ( double betrag)

    kontoStand ~ kontoStand - betrag ;

    public void einzahlen( double betrag

    kontoStand - kontoStand + betrag ;

    zie1Konto .einzah1en ( betrag ) ;

    pub1ic void transfer{ Konto

    this .abheben ( betrag ) :

    zielKonto , double betrag )

    // Zustandsänderung

    // Zustandsänderung

    c1ass Bank I

    public static

    Konto k l

    Konto k2

    void main( String[] args

    new Konto( 4711 , 120 .0 ) ;

    new Konto( 8015 , 700 .0 ) ;

    kl .transfer( k2 , 20 .0 ) ; // Zustandsänderungen

  • 181 11 R

  • 11 Ref erenz en 185

    bare Objekte ctnnnm a blc ohjects) . Bei jeder verändc rung ;10 eine m St ring-Objektwird ein nettes Objekt mit aktuellem Inhalt angelegt und das alte Objekt d urch d ieCarbagc Collcction entsorgt, sofern keine weite re Referenz darauf zcigl. Dieses Ver-fahren ist aufwän dig und bei häufigen s t r Inq-xran tp ulano ncn un pcrformant (s .u.) .Jedoch entsteh, für Verwe nder da d urch der A I/schein e ines intu itiven Wertkopie-Verhaltens wie bei primitiven Datentypen.

    In Abb ildung 11.5 werden d ie internen Abläufe deutlich : Durch die Zuweisung b =arcfercnxicrcn d ie Objckrvartablcn a lind b da sselbe Objekt. Durch Verä nderu ng vo na wird e in ncucs String-O bje kt erzeugt, auf das die Referenz a verwe ist , währendd ie Rcfcrc-nz b noch auf da s alte, unveränderte St.r i.nq-Objckt zeigt.

    String a , b ;

    a = "Ha l l o" ; b a ;a e ~ l l la llo

    b'-------'a = a + " Wel t " ;

    Dass es sich bei e ine r S't r i.nq-Variablcn um eine Objektreferenz handelt , wird je-doch bei s tring-vergleicben deutlich : String-Variah len entha lten die Referenz ihresst r Lnq-Objckrs. Anwendung des vergtetchsopcrarors == bewi rkt so mit keinen ill-haltlieben Vergleich der zcichcnkeuen , sonde rn den Vergleich der Ref erenz elI:

    String a new String ( " Ha l l o " I ; // String-Objekt erzeugt

    String b new St ring ( " Ha l l o " I ; // Weiteres String-Objekt

    boo l e a n test ~ ( a == b I ; // Vergleich liefert fa~sEl !

    Die s t r mq-vo riablc n a und b rcfe renzlercn separate Objekte gleichen Inhalts. So -mit enthalten sie unt erschiedliche Referenzen lind deren Vergle ich mittels == liefenfals e. Natürlich ist es wichlig, Strtngs au ch inhaltlich vergle ichen zu können: DieKlasse String stellt z ahlreiche stetboden [ ür lecnn f ortabie StrillgojJeratiollell zurVerfügung [SUN05CI. Die Methoden sind au f jeder St r Lnq-Rcfcrco z aufrufba r. Dazuge hö rt auch die Methode e qua ls () zum inhaltlic hen s t r i nq-v crglcicb .

    if( a .equals( b) ) IO . writeln( "Gl e i c h " ) ;

    i f ( a .equals( "Hallo" ) ) IO .w r iteln( " Gl e i c h " ) ;

    Da Veränderungen von st r i nq-Objcktcn ze itaufwändig sind, sollten hiiuflg vcrän -dt.-rrc Zeichenketten effektiver mittels de r Klasse StringBuffer dargestellt werden.

    11 .4.1 Oie Klasse StringBuffer

    Im Gegensatz zu St r i nq-Objektc n kö nnen StringBuffer-Objektc verä nde rtwerden , ohne dass jeweils ein ncucs Objekt crsrollt wird. Deshalb geschehe n Vcrän -

  • 186 Jl R(:!erellzell

    dcrungen an StringBuffer-Objekten deutlich schneller als an Strings. Auch dieKlasse StringBuffer iSI Te il des Standard-Pake ts java . l a n g.

    Zum Erzeugen von StringBuffer-Objekten iSI ein ex pliziter Konstrukteraufrufe rfo rde rlich (es stehen versc hiedene Kon strukture n zur Ve rtü gung ); der «Operatorkann nicht angewandt werden. Stattdessen stehen für alle relevanten Datentypennöeriadene Versionen der Methode append () zur Verfügung - sowie zahlreicheweitere Metboden [SUN05C] :

    StringBuffer sb = new StringBuffer ( " Ha l l o " );

    char x = 'a ' ;

    // überladene Var ianten von append für die Typen :

    // char , int , lang , float , double , String , char[J

    sb - sb .append ( x ); // Erweitern der Zeichenkette um x

    String s = sb .toString() ; // Inhalt von sb als String

    Der deutliche Pcrforma nzunrcrsch tcd zwischen String- und StringBuffer-Operationen kann durch e in Testprogramm mit Stopuhrfunktlon ermittelt werden:

    class StringBufferTest I

    public static void main( String [] args )

    lang start , e nde ;

    int n - IO .promptAndRead Int( " Wi e oft : " ) ;

    String str = "Hallo" ;

    start = System .currentTimeMillis() ;fo rt i n t i=l ; i

  • 11 Ref erenz en 187

    St r i ng- O pcration me rklic h langsa me r, währe nd die StringBuffer-O pe ra tio nnoch leeine messbare Zeit erfordert .

    Seit Ja vaS steht d ie Klasse StringBuilder m it äq uiva lente r I'un knonahtär zur Ve r-fügu ng. Diese isl im Gegensatz zu StringBuffer allerdings nicht sy nchronisiertlind somit nicht-rhrcadst cher, dad urch aber noch perfo rmunter als StringBuffe r .

    11.4.2 OleMethode t oString ()

    Jede Java-Klasse kann die Methode pub l ic String t o St ring () implementie-ren. Die Met hode kann auf jedem Objekt direkt aufgerufe n we rden , s ie wird jedochautomatisch allfgerufell, wenn e ine Objektinstan z an eine Ausgabemethode wieSystem . out . p r i rrt Ln () üb ergehen wird , Es kann s ich dabei um Konsole naus-gaben aber auch um das Schre iben in eine Datei hand eln . In der Meth ode muss einbeliebiger SlrinR z usa m mengestellt und z urüct..'[!,e/ieje ,.t werden.

    Auf die se w e ise ka nn das Objekt c lnc repräsentattrc uescöreioung seiner selbst lic-fern, typischerw eise ei ne String-Rcpräsentanon sei nes akt uellen Zustands (Attribut-hd cgung). Bei Ausgabeoperationen wird dan n nicht die Objektkennung verw endet,so nde rn d iese Stnn g-Rcpräscntanon.

    class Mitarbeiter (

    private String name ; private doub l e geha lt ;

    public Mita rbeiter( Stri ng n , double 9 )1

    na me : n ; gehalt ~ g ;

    public String t oString()

    Str ing zustand - name + " " + geha lt ;

    return zustand ;

    c Las s Ausga be {

    public s tatic void main ( String l l args ) (

    Mitarbeiter ml = new Mitarbeiter ( "Me i e r " , 3000 ) ;

    I O .writeln( " Ob j ektin f o : " + ml ) ;

    IOb j e kt i n f o : Meier 3000 . 0

    - Konsole -

    11.5 Kein Durchbrechen der Kapselung durch ReferenzenAuf Grun dlage unsere r Kenntnisse so ll knapp au f dieses fortgeschritte ne re The maeingegangen werden: Ein Ln terlaufens des Prinz ips de r Kapselurig bei privaten Atr-nb uren mittels Hefere nzen muss ve rhindert we rden.

  • 188 11 Rt:!e rellz ell

    Klassen ge währle isten die Konsistenz des inne ren Zustands ihrer Objekte durch Kap -sclung ihrer privaten Attribute. Durch geeigne te vorgeschaltete Zugriffsmethode nwerden nur zulä ssige interne zusrandsänderungcn durchgefü hrt. Falls es sich Ulll At-tribute eines primitiven Datentyps handel t gilt die Regel , da ss sich blo ße gcr-Methoden zur Abfrage der Armbur-wert e nicht sch ädlich auf den inneren Zustan ddes Objekts auswirken können. Ilandelr es sich be i Attributen jedoch um Refe ren ze nauf Objekte, sind die zusammenhä nge komplizierter. Wir betrach ten eine KlasseMitarbeiter, die ÜIX'f ein privates finales Attribut vom Typ der Klasse Kontove rfügt. Dessen Zustand sei vo n Außen nich t d irekt manipulierbar; nur durch Mc-rhoden der Klasse Mitarbeiter sollen daran z usrandsändcrun gen vorgenommenwerden können.

    class Konto I

    private int kontoNr ; private double saldo ;

    public Konto( i nt kn , double sd ) t

    kon t oNr '" kn ; saldo" sd ;

    public void einzahlen ( double b < saldo . saldo + b rpublic void abheben ( double b l saldo - saldo - b , l

    public int getNr () < return kontoNr ; lpublic double getSaldo () < return saldo ;

    class Mitarbeiter

    private f inal Konto giro = new Konto l 4711 , 0 .0 ) :

    private String name ; private double gehalt :

    public Mitarbeiter ( String n , double 9 ) (

    name - n ; gehalt - g :

    public void za hleGehal t( ) { giro . einzahlen ( gehalt ) :

    puhlie Konto getKonto() { return giro:} // Falsch ! !

    /1 ...

    Final ist die Obje ktreferenz giro, nicht jedoch der Zustand des rcfcrcnzrcrrc n Ob-je kts. Somit wirkt s ich die harmlos erscheinende Methode getKonto () kontrapro-duktiv aus: Ein Aufrufer erhält dadurch d ie Original- Referenz au f das private Attributgiro und kan n mittels diese r Referenz dessen Zusta nd und somit letztlich auch de nZustand der Klasse Mirarbeiter willentlich manipulieren - die intendierte Kapsdungwird mittels Referenz un terlaufen:

    Mitarbeiter m '" new Mitarbeiter ( " Me i e r", 3000 ,0 ) :

    Kon t o konto m.getKonto () ;

    konto , abheben ( 1000 .0) : /1 Ausplündern des Mitarbeiters m

  • 11 Referenzen 189

    Soll die gcr-Mcrhode nicht ganz entfalle n. so IllUSS in d ieser eine separate Kopie desinterne n Objekts (defensiro cop)') erste llt und d ie Refe re nz dara uf zurückgegebenwerden:

    public Konto getKonto() ( // Ko r r e kt!

    Kon t o kopie - new Kont o ( giro .getNr ( ) , gi ro . getSa l do() ) ;

    retu rn kopie ;

    Mir dieser Referenz kann der der Aufrufer bel iebig arbeit en, o hne de n Zustand einesMirarbeirer-Objekrs zu verä ndern. Die Kapselurig wird bewahrt. (Wieder e inmal istes erfo rde rlich, eine Objekt kopic zu ersrellen.)

    Jedoch birgt nicht nur das Zurückliefern von Heferenzen e in Gefahrenporenztat, son-dern auch das zu unbedarfte Entgegennehmen von Refe renzen zur tmrtahsterungvon Attributen. Betrach ten wir als spezie lles Beispiel Konsrrukrore n. Werde n diesezu naiv formulie rt. so ermöglichen sie ehenfalls ein Unte rlaufen der Kapselurig.

    class Mi tarbeiter

    privat e final Konto g iro ;

    p r i va te St r i ng name ; p r i v a te d oub le g e halt ;

    publ i c Mitarbeiter( String n , double g , Kon t o k ) (

    na me

    g iro

    g e halt - g ;

    II direkte Zuweisung -problematisch!

    publ i c void z a h l eGe ha l t ( ) { g i ro .einzahlen( gehalt ) ; I

    11 ...

    Denn über d ie heim Aufruf des Konstruk tors übergebe ne Refere nz hat de r v erwen-de r Zugriff au f das dam it d irekt initialisicrtc pr ivate Attribut giro und kann dessenZustand über die Refe renz so mit vo n Augen steuern - die intendierte Kapsdungwird un terlaufen:

    Kon to konto new Konto( 47 11 , 0 .0 ) ;

    Mi t arbei ter m - new Mi t arbei t e r ( "Me i e r", 2500 .0 , konto ) ;

    kon t o . abheben ( 1 000 . 0 ) ; 11 Ausplündern des Mitarbeiters m

    Um dies zu ve rme tden darf der Konstruktor d ie erhaltene Konto -Refere nz nicht d i-rekt dem Attribut giro zuweisen. Stattdessen wird im Konsrruktor eine neue Kopiecdefeustre co/~r) des erhaltenen Ko nto-Objekts e rste llt; mit der Referenz auf dieseKopie wird das Attribut g iro initiahsicrt und somit desse n Kapseleng bewah re

    clas s Mi t arbeiter

    p riv a t e final Konto giro ;

    p r iva t e St ri ng na me ; p r iva t e doub l e gehal t ;

    p ubl ic Mi t a rbei ter ( Str ing n , dou ble g , Kon t o k ) (

    na me n ; gehal t = g ;

    giro ne w Konto ( k .getNr( ) , k . getSal do ( ) ) ; II korrekt!

  • 190 JJ Rt.:!erellzell

    public vo id za hl e Geha l t ( ) { g i ro . e inz a hlen ( gehalt) ; f

    / I ...

    Das Gesag te g ih natürlich für jede Methode , die als Pa ramete r e ine Refe re nz c ntgc-gennimmt und diese einem e rnsp rech enden Attribut zuweist.

    Fazit: Immer wenn man ei ne Methode oder speziell e inen Konstruktor sch reib t, dieein von Außen geliefertes Ob jekt an ein Attribut übergeben, ist zu fragen: Kann undda rf sich de r Zustand des gelieferten Obj ekts verä ndern. Ist dies nicht rolcnerbar, somuss eine defeustre Kopie des Objekts erstellt und d ie Refe renz au f diese Kopie stattder Referenz auf das übergebene O riginal der inte rnen Datenst ruktur bzw. dem Att-ribut zugewiesen we rden. Ebe nso ist stets zu hinterfrage n, ob es sinnvoll ist, eineReferenz au f ein in se inem Zusta nd veränderliches Attribut an einen Aufrufer zu-rückzullefern. Oft wird man starrdessen die Refere nz au f ei ne defe nsive Kopie zu-rückliefern. Sehr anschaulich form uliert des [BL004l: "The Ilost objcct should not!el/k roferences to any Inner Part objcrt - it musr not pass rcfercnccs as argumcnts orrctum valucs of any mct hod [c..]."

    Def ensu-esProgrammtoren be deutet in diesem Zusamm e nha ng, e in eventuelles Un-terlaufen der Kapselung du rch Clien ts der Klasse scho n im Ansatz zu verme iden.Wenn e ine Klasse über Attribute ve rfügt , deren innerer Zusta nd ve rände rbar ist (//11/ -tobte objects) und es diese von Verwendern erhält oder an diese zurü ckliefe rt. solltesie dabei stets eine defensive Kopie d iese r Kompo nenten erste llen . Tut die Klassedies nicht, so ve rtraut sie blind dara uf dass ihre Clicnrs den Zustand ihrer betreffe-nc n Attribute nu r konsistent verändern. Dies sollte in der Doku mentation der Klassejedoch ausdrücklich vermerkt we rden - dad urch überne hmen die Clicn rs die ver-antwortung für alle d urchgeführte n zusrandsändcrungcn [BL004].

    Eventuel l sollen nac h der lninalislcrung von O bjekten sogar keine rlei Zustandsü nde-rungen mehr zuge lassen werde n. Dies bc zc k-hnc t das lJesigll -Kollz

  • 11 Ref erenzen

    c l ass Datum (

    public Datum (

    tg '" tag ;

    1/ Fester Zeitpunkt - unveränderlich

    Ln t tag , Lnt; mone t , Ln t jahr) (

    mon'" mona t ; j r "" jahr ;

    19 1

    public final i n t tg . mon , j r ;

    Es ist s innvoll, den Zustand einer Klasse so weni g veränderbar wie möglich zu ges-talten. Jedes Attribut sollte somit final se in, dessen Zustand sich n icht ändernmuss, Die ko mplette lnitialisk-rung vo n Objekten sollte bereits durch den Konxtruk-ror oder eine statische Feetory e rfolgen .

    11.6 BeispielanwendungEine Klasse Bruch soll Pun kno nalnä r zum Bruch rec hnen mit rarto nalen Zahlen zurVerfügung stellen. Ocr zustand ei nes Bruch-Obje kts ist der \X'en der finalen g;mz-zahligcn Attribute zaehle r lind nenner. Im Konstrukt or wird ein nenne r-w ertvo n 0 abgefangen und willkürlich auf den We rt 1 gesetzt, sowie der Bruch ge kürz tunter verwe nd urig der pr ivate Hilfsmethodc ggT ( ) , d ie den größten ge me insame nTei ler zwcicr ganze r Zahlen ermittelt.

    Die Methode toSt ring () d ient zur s t r i nq-Rc präscntarion und Konsole nausgabeei nes Bruchobjekts. Die Methode kehrWert () e rzeugt ei nes neucs Bruchobjekt alsKehrwert des aufrufe nden Bruchobjekts und die Methode negiere () d ie Negat ioneines Bruchobjekts als ncuc s Bruchobjek t. Die Met hode ke h r We r t () profitiert in-k m vo n den Mechanismen, die bcretrs in den Konst ruktor der Klasse e inge bautwurden.

    Ferner ex istieren die Metho den add () und mul t () zur Add ition bzw. .Muhiplikat i-on zwcicr Brüch e gem;iI~ der Regeln der Bruchrechnung. Die Met hoden we rden aufeine m Bruch-Objekt aufgerufen und erha lten den Verwe is auf ein weiteres Br-uch-Obje kt als Parameter. Inte rn wird das Result at der Rechenoperation in eine m ncucnBruch-O bjekt gespeiche rt und dieses (dank Konsrrukror ge kiirzt) zurückgegeben.

    Die Metho de istGleich () p rüft. ob das aufrufende Bruch-Objekt den gleiche nw ert besitzt wie das als Parameter übe rgeben e Bruch-Obje kt. Die Methode po-tenz () berechn et die gan zzabbge p-re Potenz des aufrufenden Bruch-Objekts undgibt diese als ncuc s Bruch-Objekt zurü ck . Dazu wird inte rn auf die Met hodemul t () zurückgegrttfen .

    Die Selbst refe renz this sorgt im Konstmkr or für Namenseindeut igke it und Selbst -bczug bei m Kürzen und d ient in den Methoden add (), muI t () undi s t Gl e i c h () zur syntaktische n Hervo rhebung. In der Methode p o t e n z () wirdex plizit auf die au frufende Bruch-Instanz zug egr iffen, um die mehrmalige Multipli-kation des Bruches mit s ich se lbst darzustellen .

    Durch die verfügbaren Methoden wird ein verfügbares Br uch-Objckt att ribut iv nichtmehr verändert. Die Objek te der Klasse Bruch sind immnatble.

  • 192 Jl R(:!erellzell

    ln de r aus führbaren Klasse Bruchrechner werden einige Methoden der KlasseBruch tesrwe tse aufgerufe n. Auf eine expliz ite Benut zerführu ng wurde ve rzichte t.

    c lass Bruch (

    private final int zaehler ; private final int nenner;

    public Bruch ( int zaehler , int nenner) {

    if( nenner == 0 )

    IO .writeln( " Un zu l

  • 11 Referenzen

    public double dezimale) I return (double)zaehler/nenner ;

    public boolean istGleich{ Bruch b I I

    return this .zaehler==b .zaehler && this .nenner~= b .nenner ;

    193

    Entgegennahme zurück gelieferter Bruch-Referenzen :

    bl.add(b2) ; IO . writeln( " Br u c h : + b3 I ,

    b l .mult (b2) ; 10 .writeln( " Br u c h : + b3 I ,

    bl .potenz( 3 I , ro . wr i te tn r " Br u c h : + b3 I ,

    p riv a t e statie iot ggT( iot a , iot b ) { 1/ Euklid-Algorithmus

    if( b < 0 b ~ -b ö

    iot r -a , b ,while ( r' ! = 0 I { a b , b r r r ~ a , b , {r e t urn b ,

    class Bruchrechner I // Bloße Testklasse

    p ublic statie vo id main ( String[ J args )

    Bruch b l - new Bruch( 2 ,3) ; Bruch b2 - new Bruch( 4,5 ) ;

    IO .writeln( " De z i ma l - " + b I . d e z ima l ( ) ) ;

    Bruch b3;

    //

    b3

    b3

    b3

    /1 Direkte Verwendung zurück gelieferter Referenzen :

    IO .writeln( " Br u c h : + bl .add( b2 ) ) ;

    IO .writeln( "Br uc h : + bl.mult( b2 ) ) ;

    IO .writeln( " Br u c h: + bI.potenz ( 3 ) ) ;

    IO .writeln( " BI' : " + b2 .add( b2 ) . p o t e n z ( 4 ) . mu l t ( b l I ) ;

    In Bruchrechner wird auch d ie direkte Verwendung der von add ( ), mu l t ( )lind p o t e nz () zurückgelieferten Referenzen gezeigt : Durch deren Aufruf wird eineallonyme Bruch-Objd~trefi'I"(,lIz geliefert, au f de r ohne vorige Zuweisung an eineseparate Objektvariable öffentliche Bruch-Methoden aufgerufe n werden kö nnen :

    IO .writeln( b 2 . a d d ( b2 ) . p ot e n z ( 4 ) . mu l t ( b l ) ) ;

    Es wird von links nach rechts de r Anfruftsette folgend ausgewertet: Der Bruch b2wird zu sich se lbst addiert, das Ergebnis sofort zur -t-rcn Pote nz erhoben, mit demBruch b l multipliziert und das Resultat via 10 . wri teln () d urch Aufruf vo n t o -String () au f de r zule tzt zurückgelieferten Bruch -Referenz ausgegeben" Da keineObjektvariable die Objekte rcfcrcnzicr t lind im Spe icher hält, würden sie nach Ah-arbciumg de r 'l..ciJc im Programmverlauf von de r Garbagc Collccnon entsorgt.

  • 191 Jl R(:!erellzell

    Bislang fehlt uns die Möglichkelt . zahlreic he primitive Varia blen oder insbesonderezahl reiche Objek te in geordneter Weise zu speichern und wieder darauf zuzugreife n.Dies ist jedoch eine unab din gbare Voraussetzung, Ulll anspruchsvollere objektorten-uc rrc Prog ranune zu real isieren. Im nächsten Kapitel werde n deshalb A rm y '; als gc-e igne te un ivc.-rsc lk- J)(Jleli hebiilter vo rgeslt..'llt .

    11 Referenzen11.1 Primitive Datentypen11.1.1 Zuweisungen primitiver Datentypen11.1.2 Primitive Datentypen als Methodenparameter11.2 Objeklreferenzen11.2.1 Entfernen von Referenzen - Konstante null11 .2.2 Zuweisungen zwischen Referenztypen11.2.3 Vergleiche zwischen Objektvariablen11.2.4 Kopieren von Objekten11.2.5 Finale Objektvariablen11.2.6 5elbstverweis mittels this -Referenz11 .2.7 Anonyme Objekle11.3 Objekte als Methodenparameter11 .3.1 Rückgabe von Objeklreferenzen11.3.2 Effekte von Methoden11.4 Die Klasse String11 .4.1 Oie Klasse StringBuffer11.4.2 OleMethode t oString ()11.5 Kein Durchbrechen der Kapselung durch Referenzen11.6 Beispielanwendung

    /ColorImageDict > /JPEG2000ColorACSImageDict > /JPEG2000ColorImageDict > /AntiAliasGrayImages false /CropGrayImages true /GrayImageMinResolution 149 /GrayImageMinResolutionPolicy /Warning /DownsampleGrayImages true /GrayImageDownsampleType /Bicubic /GrayImageResolution 150 /GrayImageDepth -1 /GrayImageMinDownsampleDepth 2 /GrayImageDownsampleThreshold 1.50000 /EncodeGrayImages true /GrayImageFilter /DCTEncode /AutoFilterGrayImages true /GrayImageAutoFilterStrategy /JPEG /GrayACSImageDict > /GrayImageDict > /JPEG2000GrayACSImageDict > /JPEG2000GrayImageDict > /AntiAliasMonoImages false /CropMonoImages true /MonoImageMinResolution 599 /MonoImageMinResolutionPolicy /Warning /DownsampleMonoImages true /MonoImageDownsampleType /Bicubic /MonoImageResolution 600 /MonoImageDepth -1 /MonoImageDownsampleThreshold 1.50000 /EncodeMonoImages true /MonoImageFilter /CCITTFaxEncode /MonoImageDict > /AllowPSXObjects false /CheckCompliance [ /None ] /PDFX1aCheck false /PDFX3Check false /PDFXCompliantPDFOnly false /PDFXNoTrimBoxError true /PDFXTrimBoxToMediaBoxOffset [ 0.00000 0.00000 0.00000 0.00000 ] /PDFXSetBleedBoxToMediaBox true /PDFXBleedBoxToTrimBoxOffset [ 0.00000 0.00000 0.00000 0.00000 ] /PDFXOutputIntentProfile (None) /PDFXOutputConditionIdentifier () /PDFXOutputCondition () /PDFXRegistryName () /PDFXTrapped /False

    /CreateJDFFile false /Description > /Namespace [ (Adobe) (Common) (1.0) ] /OtherNamespaces [ > /FormElements false /GenerateStructure false /IncludeBookmarks false /IncludeHyperlinks false /IncludeInteractive false /IncludeLayers false /IncludeProfiles false /MultimediaHandling /UseObjectSettings /Namespace [ (Adobe) (CreativeSuite) (2.0) ] /PDFXOutputIntentProfileSelector /DocumentCMYK /PreserveEditing true /UntaggedCMYKHandling /LeaveUntagged /UntaggedRGBHandling /UseDocumentProfile /UseDocumentBleed false >> ]>> setdistillerparams> setpagedevice