Casten van objecten

Pagina: 1
Acties:

Onderwerpen


Acties:
  • 0 Henk 'm!

  • robinP95
  • Registratie: Mei 2014
  • Laatst online: 30-09 16:32
Ik heb al een tijdje programmeren links laten liggen en laatst weer opgepakt.
Nu loop ik vast bij het kunnen begrijpen van casten.

Stel: een superklasse Winkel met de subklasse Supermarkt

Winkel winkel = new Winkel();
Supermarkt jumbo = new Supermarkt();

jumbo = (Supermarkt)winkel;

Wat is hierboven nu gebeurd? Als ik het goed begrijp is het object "winkel" gecast naar een Supermarkt object als variabele "jumbo". Maar is "jumbo" nu ook een echt een normaal Supermarkt object, of bevat dit object iets extra's aangezien hij gecast is vanaf een Winkel object?


Wat hieronder staat, doet dit hetzelfde als hierboven beschreven?

Winkel C1000 = new Supermarkt();


Alvast bedankt,
-Robin :*)

Acties:
  • 0 Henk 'm!

  • Caelorum
  • Registratie: April 2005
  • Laatst online: 07:48
Het eerste is wat ze noemen upcasting en is vaak al niet eens mogelijk in een taal. Als het wel mogelijk is ligt het maar net aan de taal hoe er mee wordt omgegaan.
Het tweede doet niet wat erboven staat. In het tweede voorbeeld creëer je een object van het type Supermarkt en behandel je het als een Winkel. Je kan dan dus de methodes zoals gedefinieerd in Winkel aanroepen op het Supermarkt object, maar niet die in Supermarkt. Dat kan handig zijn in het geval van meerdere typen Winkels die je toch allemaal als hetzelfde wilt behandelen op sommige plekken.

Acties:
  • 0 Henk 'm!

  • Sebazzz
  • Registratie: September 2006
  • Laatst online: 12-10 15:56

Sebazzz

3dp

Casten moet je zien als tegen de compiler zeggen: "Ik weet wat het type van deze variabele is, ga maar uit van die aanname".

[Te koop: 3D printers] [Website] Agile tools: [Return: retrospectives] [Pokertime: planning poker]


Acties:
  • 0 Henk 'm!

  • .oisyn
  • Registratie: September 2000
  • Laatst online: 02:34

.oisyn

Moderator Devschuur®

Demotivational Speaker

Eigenlijk helemaal niets. Het statische type zoals je compiler er tegenaankijkt is gewijzigd, maar het object is nog exact hetzelfde. Afhankelijk van de taal (bij de meeste eigenlijk wel) krijg je een error bij het casten, want 'winkel' is nou eenmaal geen (subklasse van) Supermarkt.
Maar is "jumbo" nu ook een echt een normaal Supermarkt object, of bevat dit object iets extra's aangezien hij gecast is vanaf een Winkel object?
Geen van beide. Het is een Winkel object. Eigenschappen die uniek zijn voor een Supermarkt zal het object niet hebben.
Wat hieronder staat, doet dit hetzelfde als hierboven beschreven?

Winkel C1000 = new Supermarkt();
Ja en nee. Het doet hetzelfde in de zin dat ook hier anders tegen het object aan gekeken wordt door de compiler. Je zult hier alleen geen runtime error krijgen aangezien elke Supermarkt per definitie ook een Winkel is. Het object waar 'C1000' naar wijst is en blijft een Supermarkt, alleen limiteer je jezelf tot de eigenschappen die alle Winkels met elkaar delen.

Je kunt 'C1000' vervolgens weer downcasten naar een Supermarkt, en in dat geval krijg je geen errors aangezien het object waar 'C1000' naar verwijst in werkelijkheid een Supermarkt is.
Caelorum schreef op zaterdag 10 januari 2015 @ 14:56:
Het eerste is wat ze noemen upcasting en is vaak al niet eens mogelijk in een taal.
Andersom ;). Van derived naar base heet upcasten (en kan in de regel impliciet), van base naar derived heet downcasten (en moet doorgaans expliciet)

[ Voor 18% gewijzigd door .oisyn op 10-01-2015 16:12 ]

Give a man a game and he'll have fun for a day. Teach a man to make games and he'll never have fun again.


Acties:
  • 0 Henk 'm!

  • Herko_ter_Horst
  • Registratie: November 2002
  • Niet online
Aangenomen dat je een inheritance-relatie hebt tussen Winkel en Supermarkt (Supermarkt extends Winkel), heeft casten alleen zin/gaat het alleen goed als je een Winkel hebt waarvan jij als programmeur weet dat het een Supermarkt is.

Dus bijv.
code:
1
2
Winkel jumboWinkel = new Supermarkt();
Supermarkt jumboSupermarkt = (Supermarkt)jumboWinkel;

Dit werkt omdat het object waar jumboWinkel naar refereert een Supermarkt is.

Wat dus niet werkt is:
code:
1
2
Winkel gammaWinkel = new Bouwmarkt();
Supermarkt gammaSupermarkt = (Supermarkt)gammaWinkel;

Het moge duidelijk zijn waarom dit niet werkt.

En wat dus ook niet werkt:
code:
1
2
Winkel winkel = new Winkel();
Supermarkt supermarkt = (Supermarkt)winkel;

Dit werkt ook niet, want winkel is geen Supermarkt.

Wat wel altijd kan, zonder cast, is de andere kant op:
code:
1
2
3
4
Supermarkt jumbo = new Supermarkt();
Winkel jumboWinkel = jumbo;
Bouwmarkt gamma = new Bouwmarkt();
Winkel gammaWinkel = gamma;


tl;dr: casten is geen magie, het is een aanwijzing voor de compiler om iets goed te keuren wat hij zelf niet kan weten, maar wat jij als programmeur wel weet.

[ Voor 9% gewijzigd door Herko_ter_Horst op 10-01-2015 16:30 ]

"Any sufficiently advanced technology is indistinguishable from magic."


Acties:
  • 0 Henk 'm!

  • farlane
  • Registratie: Maart 2000
  • Laatst online: 14-10 00:53
robinP95 schreef op zaterdag 10 januari 2015 @ 14:26:
Stel: een superklasse Winkel met de subklasse Supermarkt

code:
1
2
3
4
Winkel winkel = new Winkel();
Supermarkt jumbo = new Supermarkt();

jumbo = (Supermarkt)winkel;
Als je moet downcasten is het meestal goed om te kijken of je klasse hiërarchie wel ok is, het wordt vaak als een 'code smell' gezien

Somniferous whisperings of scarlet fields. Sleep calling me and in my dreams i wander. My reality is abandoned (I traverse afar). Not a care if I never everwake.

Pagina: 1